refactor(0.1.14-P1): 内核归位——game/ 按引擎架构重排(零行为漂移)

结构(旧 game/core+engine → 新 engine/ 域):
- engine/kernel/  时钟/随机/插件协议/fxqueue/timesense/format/urgency/guide/names(原 core)
- engine/narrative/  legacy/报告/列传/谱系/年轴(原 core 叙事族)
- engine/runtime/   World/creation/pcgen/ApiFacade/capabilities/pluginManager/boot/clocks + Systems/*(12 系统)
- engine/sim/     Market(未来 WorldSim 同行)
- 旧 game/core、engine/systems、engine/world.ts 等路径全部废弃(无 re-export 兼容层)

验证:35 套件/967 测试全绿(金钟罩三档零漂移=纯搬迁无行为变化)
typecheck 0 error
This commit is contained in:
2026-08-23 13:23:25 +08:00
parent 2528226a9f
commit ff6df8054c
89 changed files with 281 additions and 281 deletions
+2 -2
View File
@@ -1,10 +1,10 @@
import { useState } from 'react'
import { useGameStore } from '../store'
import { applyEventChoice, rankPower } from '../../game/engine/systems/events'
import { applyEventChoice, rankPower } from '../../game/engine/runtime/Systems/events'
import { eventCategoryName } from '../../game/data/events'
import { describeRealm } from '../../game/data/realms'
import { Character } from '../../game/types/domain'
import { combatPowerOf } from '../../game/engine/systems/combat'
import { combatPowerOf } from '../../game/engine/runtime/Systems/combat'
import { FORMATIONS, FormationId } from '../../game/data/formations'
import { ModalShell } from './ModalShell'
+1 -1
View File
@@ -1,5 +1,5 @@
import { useGameStore } from '../store'
import { GUIDE_STEPS, computeGuide, guideAdvance } from '../../game/core/guide'
import { GUIDE_STEPS, computeGuide, guideAdvance } from '../../game/engine/kernel/guide'
export function GuideStrip() {
const world = useGameStore((s) => s.world)
+4 -4
View File
@@ -5,12 +5,12 @@ import { describeRoots, ROOT_GRADE_NAMES } from '../../game/data/elements'
import { TRAITS } from '../../game/data/traits'
import { TECHNIQUES } from '../../game/data/techniques'
import { ITEMS, ARTIFACT_POWER } from '../../game/data/items'
import { combatPowerOf } from '../../game/engine/systems/combat'
import { lifespanOf } from '../../game/engine/systems/lifecycle'
import { perAttemptChance } from '../../game/engine/systems/cultivation'
import { combatPowerOf } from '../../game/engine/runtime/Systems/combat'
import { lifespanOf } from '../../game/engine/runtime/Systems/lifecycle'
import { perAttemptChance } from '../../game/engine/runtime/Systems/cultivation'
import { POSTS, POST_ORDER } from '../../game/data/posts'
import { ModalShell } from './ModalShell'
import { buildBiography } from '../../game/core/biography'
import { buildBiography } from '../../game/engine/narrative/biography'
function aspName(c: Character): string {
const map: Record<string, string> = {
+1 -1
View File
@@ -1,5 +1,5 @@
import { useGameStore } from '../store'
import { LegacyArch } from '../../game/core/legacy'
import { LegacyArch } from '../../game/engine/narrative/legacy'
import { sBell } from '../sound'
import { ModalShell } from './ModalShell'
+1 -1
View File
@@ -1,5 +1,5 @@
import { useGameStore } from '../store'
import { computeUrgency } from '../../game/core/urgency'
import { computeUrgency } from '../../game/engine/kernel/urgency'
export function UrgentBadges() {
const world = useGameStore((s) => s.world)
+1 -1
View File
@@ -1,4 +1,4 @@
import { FxGate, FxKind } from '../game/core/fxqueue'
import { FxGate, FxKind } from '../game/engine/kernel/fxqueue'
import { seasonOf } from '../game/data/season'
let gate: FxGate | null = null
+1 -1
View File
@@ -1,6 +1,6 @@
import { useGameStore } from '../store'
import { npcById } from '../../game/data/npcs'
import { giftNpc, makePeace, marryNpcFamily, calcGiftGain, GIFT_TIERS } from '../../game/engine/systems/diplomacy'
import { giftNpc, makePeace, marryNpcFamily, calcGiftGain, GIFT_TIERS } from '../../game/engine/runtime/Systems/diplomacy'
import { useMemo } from 'react'
import { MAJOR_NAMES } from '../../game/data/realms'
+2 -2
View File
@@ -1,7 +1,7 @@
import { useGameStore } from '../store'
import { MISSIONS, missionById } from '../../game/data/secrets'
import { sendMission, recallAll } from '../../game/engine/systems/missions'
import { combatPowerOf } from '../../game/engine/systems/combat'
import { sendMission, recallAll } from '../../game/engine/runtime/Systems/missions'
import { combatPowerOf } from '../../game/engine/runtime/Systems/combat'
import { useState } from 'react'
import { describeRealm, MAJOR_ORDER } from '../../game/data/realms'
import { FORMATIONS, FormationId } from '../../game/data/formations'
+1 -1
View File
@@ -1,5 +1,5 @@
import { useGameStore } from '../store'
import { computeGenealogy } from '../../game/core/genealogy'
import { computeGenealogy } from '../../game/engine/narrative/genealogy'
import { describeRealm } from '../../game/data/realms'
import { Character, FamilyState } from '../../game/types/domain'
import { useState } from 'react'
+5 -5
View File
@@ -1,11 +1,11 @@
import { useState } from 'react'
import { useGameStore } from '../store'
import { computeLegacy, resolveLegacy } from '../../game/core/legacy'
import { resolveLegacy as doesIt } from '../../game/core/legacy'
import { computeLegacy, resolveLegacy } from '../../game/engine/narrative/legacy'
import { resolveLegacy as doesIt } from '../../game/engine/narrative/legacy'
import { ResolveModal } from '../components/ResolveModal'
import { buildBiography } from '../../game/core/biography'
import { yearAxis, decadeLabel } from '../../game/core/yearaxis'
import { buildReport, verdictLine } from '../../game/core/legacyreport'
import { buildBiography } from '../../game/engine/narrative/biography'
import { yearAxis, decadeLabel } from '../../game/engine/narrative/yearaxis'
import { buildReport, verdictLine } from '../../game/engine/narrative/legacyreport'
void doesIt
+1 -1
View File
@@ -2,7 +2,7 @@ import { useGameStore } from '../store'
import { ITEMS } from '../../game/data/items'
import { TECHNIQUES } from '../../game/data/techniques'
import { techniqueGradeName } from '../../game/data/realms'
import { marketPrice, buyItem, sellItem, buyTechnique } from '../../game/engine/market'
import { marketPrice, buyItem, sellItem, buyTechnique } from '../../game/engine/sim/Market'
import { useMemo, useState } from 'react'
export default function MarketPanel() {
+3 -3
View File
@@ -1,9 +1,9 @@
import { useState } from 'react'
import { useGameStore } from '../store'
import { examplePlugin } from '../../game/engine/demo-plugins'
import { examplePlugin } from '../../game/engine/runtime/demo-plugins'
import { ensureFx } from '../fx'
import { SYSTEM_DEFS } from '../../game/engine/capabilities'
import { buildBiography } from '../../game/core/biography'
import { SYSTEM_DEFS } from '../../game/engine/runtime/capabilities'
import { buildBiography } from '../../game/engine/narrative/biography'
export default function SettingsPanel() {
const world = useGameStore((s) => s.world)
+2 -2
View File
@@ -12,9 +12,9 @@ import ChroniclePanel from '../panels/ChroniclePanel'
import SettingsPanel from '../panels/SettingsPanel'
import { LogFeed } from '../components/LogFeed'
import { UrgentBadges } from '../components/UrgentBadges'
import { fmt as fmtNum } from '../../game/core/format'
import { fmt as fmtNum } from '../../game/engine/kernel/format'
import { seasonOf } from '../../game/data/season'
import { seasonTint, yearRing, tideOf } from '../../game/core/timesense'
import { seasonTint, yearRing, tideOf } from '../../game/engine/kernel/timesense'
import landscapeUrl from '../../assets/gen/landscape-gold.svg'
import { GuideStrip } from '../components/GuideStrip'
+2 -2
View File
@@ -1,7 +1,7 @@
import { useMemo, useState } from 'react'
import { useGameStore } from '../store'
import { SURNAME_POOL } from '../../game/core/names'
import { RngHub } from '../../game/core/rng'
import { SURNAME_POOL } from '../../game/engine/kernel/names'
import { RngHub } from '../../game/engine/kernel/rng'
export default function NewGame() {
const go = useGameStore((s) => s.go)
+1 -1
View File
@@ -1,5 +1,5 @@
// 合成音效:鼓点·钟鸣·纸韵(Web Audio,零素材依赖)
import { RngHub } from '../game/core/rng'
import { RngHub } from '../game/engine/kernel/rng'
let ctx: AudioContext | null = null
let enabled = true
+7 -7
View File
@@ -1,13 +1,13 @@
import { create } from 'zustand'
import { World, WorldEventBus } from '../game/engine/world'
import { World, WorldEventBus } from '../game/engine/runtime/World'
import { EventDef } from '../game/data/events'
import { findEvent, applyEventChoice } from '../game/engine/systems/events'
import { findEvent, applyEventChoice } from '../game/engine/runtime/Systems/events'
import { BattleLog, ChronicleEntry, GameState, LogItem, SaveMeta, YearlyReport, SnapshotMeta } from '../game/types/domain'
import { getSlotManager, getSaveSlot } from '../game/storage/db'
import { metaFromState, updateSlotMeta } from './storeHelper'
import { GameFacade, ActName } from '../game/engine/api'
import { GameFacade, ActName } from '../game/engine/runtime/ApiFacade'
import { setSoundEnabled, sPaper, sGood, sBad, sWar, sBell, sGong, sClick, sTick } from './sound'
import type { PhaseStat } from '../game/core/clock'
import type { PhaseStat } from '../game/engine/kernel/clock'
import { seasonOf } from '../game/data/season'
export type Screen = 'boot' | 'newgame' | 'game'
@@ -63,7 +63,7 @@ export interface GameStore {
facade?: GameFacade
advancing: boolean
setNextToast: (msg: string) => void
act: (name: ActName, payload: import('../game/engine/api').ActPayload) => boolean
act: (name: ActName, payload: import('../game/engine/runtime/ApiFacade').ActPayload) => boolean
}
const LOG_CAP = 260
@@ -193,7 +193,7 @@ export const useGameStore = create<GameStore>((set, get) => ({
const elapsed = performance.now() - t0
try {
const nextInv = { ...w.state.family.inventory, stones: w.state.family.stones }
const FxGate = (await import('../game/core/fxqueue')).FxGate
const FxGate = (await import('../game/engine/kernel/fxqueue')).FxGate
const deltas = FxGate.deltas(prevInv, nextInv)
const windowRef = window as unknown as { dispatchEvent: (e: Event) => void }
windowRef.dispatchEvent(new CustomEvent('fx:drift', { detail: deltas }))
@@ -454,7 +454,7 @@ function makeBus(st: GameStore): WorldEventBus {
}
}
function actDirect(w: World, name: ActName, payload: import('../game/engine/api').ActPayload): boolean {
function actDirect(w: World, name: ActName, payload: import('../game/engine/runtime/ApiFacade').ActPayload): boolean {
if (name === 'legacy.resolve') return (w.resolveLegacyNow(), true)
if (name === 'estate.rite') return w.ancestralRite()
if (name === 'estate.sutra') return w.seekSutra()