refactor(settings): own two-phase runtime settings
Move pre-window loading, startup application, live settings mutation, toon context, quality reapply, and SettingsVM loans behind one RuntimeSettingsController. Preserve retail command behavior, ordered target publication, draft semantics, and retryable failure convergence while removing duplicate GameWindow state and feature bodies. Co-authored-by: Codex <codex@openai.com>
This commit is contained in:
parent
4eae9b4f5a
commit
fec0d94148
24 changed files with 2379 additions and 599 deletions
|
|
@ -27,13 +27,14 @@ What does NOT go here:
|
|||
## Current queue — 2026-07-22
|
||||
|
||||
- **Active structural work:** `GameWindow` decomposition. Slices 1–7 are
|
||||
complete; Slice 8 checkpoints A–F now own native callbacks, live-session
|
||||
complete; Slice 8 checkpoints A–G now own native callbacks, live-session
|
||||
composition, world-environment state, reversible device input/raw pointer,
|
||||
physical framebuffer publication, gameplay action priority, typed commands,
|
||||
and the retained-root item-drop edge outside the shell.
|
||||
the retained-root item-drop edge, and two-phase runtime settings outside the
|
||||
shell.
|
||||
`GameWindow.OnUpdate` and `GameWindow.OnRender` are typed orchestration
|
||||
handoffs and the class is 4,057 lines / 198 fields / 54 methods. Remaining
|
||||
Slice 8 settings/resource/composition/shutdown
|
||||
handoffs and the class is 3,663 lines / 162 fields / 37 methods. Remaining
|
||||
Slice 8 resource/composition/shutdown
|
||||
cleanup is active in
|
||||
[`docs/architecture/code-structure.md`](architecture/code-structure.md).
|
||||
This is the behavior-preserving prerequisite before new M4 feature bodies.
|
||||
|
|
|
|||
|
|
@ -829,11 +829,15 @@ Current movement/collision ownership:
|
|||
routers; Slice 4 moved hydration, teardown, inbound authority, network
|
||||
updates, and reusable motion-runtime policy over canonical
|
||||
`LiveEntityRuntime`. Slices 5–7 complete landblock presentation and the
|
||||
update/render frame graphs. Slice 8 checkpoints A–F now own the native
|
||||
update/render frame graphs. Slice 8 checkpoints A–G now own the native
|
||||
callback shell, live-session composition, world environment, reversible
|
||||
input/pointer lifetime, physical framebuffer publication, the sole gameplay
|
||||
action-priority graph, typed commands, and the retained-root item-drop edge.
|
||||
Two-phase runtime settings is the next checkpoint. The reconciled ledger and sequence live in
|
||||
action-priority graph, typed commands, the retained-root item-drop edge, and
|
||||
two-phase runtime settings. `RuntimeSettingsController` is the sole settings
|
||||
persistence/current-state owner, supplies the immutable pre-window snapshot,
|
||||
applies startup pacing/display/FOV/audio once, and later borrows complete
|
||||
runtime targets without replay. Explicit resource ownership and frame slots
|
||||
are the next checkpoint. The reconciled ledger and sequence live in
|
||||
`docs/architecture/code-structure.md`. This decision does not reclassify the
|
||||
remaining L.2 conformance work or Track LH.
|
||||
|
||||
|
|
|
|||
|
|
@ -34,6 +34,7 @@ after Slice 7 draw-frame cutover 4,666 lines / 196 fields / 70 method
|
|||
after Slice 8 checkpoint D 4,330 lines / 192 fields / 67 methods
|
||||
after Slice 8 checkpoint E 4,266 lines / 194 fields / 65 methods
|
||||
after Slice 8 checkpoint F 4,057 lines / 198 fields / 54 methods
|
||||
after Slice 8 checkpoint G 3,663 lines / 162 fields / 37 methods
|
||||
```
|
||||
|
||||
`GameWindow` is the single object that:
|
||||
|
|
@ -195,8 +196,9 @@ documentation, not an exhaustive allowlist):
|
|||
shared root and sibling controls.
|
||||
- `DevToolsFramePresenter -> DevToolsPanelSet -> panel/ViewModel bindings` for
|
||||
the optional developer UI.
|
||||
- `WorldRenderFrameBuilder -> RuntimeWorldFrameSettingsPreview -> SettingsVM`
|
||||
for the live settings draft preview applied before world drawing.
|
||||
- `WorldRenderFrameBuilder -> RuntimeWorldFrameSettingsPreview ->
|
||||
IRuntimeSettingsPreviewSource -> RuntimeSettingsController -> optional
|
||||
SettingsVM` for the live settings draft preview applied before world drawing.
|
||||
- `LocalPlayerPortalViewport -> LocalPlayerTeleportController ->
|
||||
GameplayInputFrameController -> InputDispatcher.Fired -> GameWindow` for the
|
||||
canonical portal/input lifetime and the host's input-action subscription.
|
||||
|
|
@ -692,7 +694,7 @@ slices. `OnClosing` delegates to the existing retryable shutdown transaction.
|
|||
Silk callbacks become narrow calls into the input, update, render, resize,
|
||||
focus, and shutdown owners.
|
||||
|
||||
Checkpoints E and F are complete. `CameraPointerInputController` owns raw pointer,
|
||||
Checkpoints E, F, and G are complete. `CameraPointerInputController` owns raw pointer,
|
||||
camera cursor/focus/scroll/sensitivity behavior; `FramebufferResizeController`
|
||||
alone publishes physical framebuffer changes. All Silk, dispatcher, retained
|
||||
UI, and optional devtools device edges are reversible, transactional, and
|
||||
|
|
@ -705,8 +707,18 @@ subscriber and preserves the accepted input-priority graph. Focused combat,
|
|||
diagnostic, and general command owners replace the remaining window command
|
||||
bodies. The retained-root item-drop edge has one reversible owner, while its
|
||||
deferred toolbar targets become inert before session retirement. `GameWindow`
|
||||
is now 4,057 raw lines / 198 fields / 54 methods. Checkpoints G–L remain
|
||||
active, with two-phase runtime settings next.
|
||||
now has no settings-store construction, duplicate settings loads, persisted
|
||||
settings mirrors, or display/quality feature bodies. `RuntimeSettingsController`
|
||||
is constructed before `Window.Create`, owns the one immutable startup snapshot
|
||||
and current/toon settings state, applies startup display/pacing/FOV/audio once,
|
||||
then borrows late-bound runtime targets without replay. Saved FOV now applies at
|
||||
startup even when devtools are disabled; this is a deliberate correction of the
|
||||
old accidental SettingsVM gate. The controller also preserves unrelated unsaved
|
||||
Gameplay draft fields when combat preferences change. `GameWindow` is now 3,663
|
||||
raw lines / 162 fields / 37 methods. Checkpoints H–L remain active, with explicit
|
||||
resource ownership and frame slots next. The Checkpoint G production App build
|
||||
is warning-free, all three corrected-diff reviews are clean, and the complete
|
||||
Release suite passes 7,553 tests / 5 intentional skips.
|
||||
|
||||
### 4.4 Exit criteria
|
||||
|
||||
|
|
|
|||
|
|
@ -107,7 +107,7 @@ accepted-divergence entries (#96, #49, #50).
|
|||
|
||||
---
|
||||
|
||||
## 3. Documented approximation (AP) — 87 active rows
|
||||
## 3. Documented approximation (AP) — 88 active rows
|
||||
|
||||
Wave-0 UI ledger repair (2026-07-10) retired stale AP-38, resolved the AP-84
|
||||
collision, restored overwritten paperdoll rows as AP-92/AP-93, and registered
|
||||
|
|
@ -217,6 +217,7 @@ AP-94..AP-112 for the confirmed retail-UI completion gaps.
|
|||
| AP-118 | An AutoWield transaction begun in active combat preserves the ready mode implied by the requested weapon. After authoritative `WieldObject`, a mode that settled without a blocker transition clears immediately; local ACE's observed pre-wield transition plus `ready -> NonCombat`, or post-wield `NonCombat -> ready -> NonCombat`, causes one normal `ChangeCombatMode` request from the trailing notice. Explicit user combat input cancels settlement. Retail's client does not need this extra request against the retail server. | `src/AcDream.App/UI/AutoWieldController.cs`; production binding in `GameWindow.cs` | Local ACE queues a trailing NonCombat callback during primary-weapon replacement and rejects an earlier request while the shuffle is busy; responding to the authoritative notice that completes that exact sequence orders the ordinary request after it without suppressing any server state | A non-ACE server that emits a different intermediate sequence can retain the settlement until a later explicit combat request, replacement, or logout clears it; peace-mode equips send none | `CPlayerSystem::AutoWield @ 0x00560A60`; `ACCWeenieObject::ServerSaysMoveItem @ 0x0058DBB0`; ACE `Player_Inventory.TryShuffleStance` / `TryDequipObjectWithNetworking` |
|
||||
| AP-119 | Equal-generation CreateObject refresh applies the packet's complete `PhysicsDesc` to the existing `EntityEffectProfile`, including replacing its network sound/PES-table/default-script description. Retail's equal-`INSTANCE_TS` branch applies the individual ObjDesc/Parent-or-Position/Movement/State/Vector/WeenieDesc tail and does not call `CPhysicsObj::set_description` again. | `src/AcDream.App/Physics/LiveEntityNetworkUpdateController.cs` (`ILiveEntitySameGenerationUpdateSink.OnDescription`); `LiveEntitySameGenerationUpdateRouter.cs` | Existing spell/projectile/portal VFX tests and connected behavior were accepted with this refresh. Slice 4 records and isolates it rather than silently changing DAT-effect ownership during an architecture extraction. | A same-generation CreateObject whose PeTable/sound/default-script fields differ from the original can replace effect lookup state where retail would retain the original table, producing a different later typed effect. | `SmartBox::HandleCreateObject @ 0x00454C80`; `CPhysicsObj::set_description @ 0x00514F40`; `docs/research/2026-07-13-retail-projectile-vfx-pseudocode.md` |
|
||||
| AP-120 | `ObjectTableWiring.ApplyEntitySpawn` publishes the CreateObject's WeenieDesc/item state before the same-generation physics update tail. Retail applies WeenieDesc after ObjDesc, Parent-or-Position/Pickup, Movement, State, and Vector. | `src/AcDream.Core.Net/ObjectTableWiring.cs` (`ApplyEntitySpawn`); `src/AcDream.App/World/LiveEntitySameGenerationUpdateRouter.cs` | Core.Net owns item-table ingestion before App callbacks and the current single-thread FIFO prevents a second network packet from interleaving; changing publication order crosses the Core.Net/App ownership boundary and requires a separately tested event transaction. | A synchronous item-table observer can see the refreshed WeenieDesc while the same object's physics/parent/state still reflects the prior snapshot; retail observers see the completed physics tail first. | `SmartBox::HandleCreateObject @ 0x00454C80`; `ACCObjectMaint::CreateObject @ 0x00558870` |
|
||||
| AP-121 | The `/framerate` command persists acdream's live ShowFps value in the modern `settings.json` Display bag after performing retail's live toggle/notice behavior. The named retail `DoFrameRate` body itself only flips `fShowFramerate` and sends `SetFramerateDisplay`; no equivalent persistence write occurs in that command body. | `src/AcDream.App/Settings/RuntimeSettingsController.cs` (`ToggleFrameRate`) | This preserves acdream's shipped L.0 cross-launch display preference while keeping the live retail mechanism and SmartBox visibility result exact; it changes no gameplay or wire state | A relaunch can retain FPS visibility where the named retail command body alone would not; a future port of retail's wider preference owner must avoid double-persisting or applying conflicting startup state | `ClientCommunicationSystem::DoFrameRate @ 0x005707D0`; `CM_UI::SendNotice_SetFramerateDisplay @ 0x0047A050`; `gmSmartBoxUI::RecvNotice_SetFramerateDisplay @ 0x004D65E0` |
|
||||
|
||||
## 4. Temporary stopgap (TS) — 38 active rows + TS-37 historical note (TS-20 retired 2026-07-16 — the later named-retail audit disproved the proposed DrawingBSP polygon filter; TS-37 is a retired-row historical note, not an active count; TS-39 retired R5-V3 — sticky seams bound to the ported PositionManager/StickyManager, radii threaded; TS-45 retired 2026-07-07 — hand-rolled `SphereCollision` replaced by the faithful CSphere family port, fixing the player-vs-monster crowd wedge; TS-3 retired 2026-07-07 — `frames_stationary_fall` accounting ported in the #182 verbatim UpdateObjectInternal rebuild, fixing the airborne falling-animation wedge; TS-41 retired 2026-07-07 — SERVERVEL synth-velocity remote body-drive replaced by the retail interp catch-up + unconditional MovementManager::UseTime, the remote-creature de-overlap #184; TS-42 retired 2026-07-19 — semantic animation completion now precedes the ordered Target/Movement/PartArray/Position tail; TS-44 narrowed again 2026-07-19 — complete orientation joined interpolation, only during-stick enqueue suppression remains)
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
# acdream — strategic roadmap
|
||||
|
||||
**Status:** Living document. Updated 2026-07-22. **M3 landed; M4 is next after the active `GameWindow` structural prerequisite.** M3's retail casting/UI, R6 locomotion/collision/projectile/teleport/radar rebaseline, deterministic fresh-login/portal world lifecycle, and final two-client portal observer flow are user-gated. The current program is the behavior-preserving ownership campaign in [`docs/architecture/code-structure.md`](../architecture/code-structure.md); Slices 1–7 and Slice 8 checkpoints A–F are complete, with the remaining composition/shutdown checkpoints active. New M4 quest/emote/character-creation feature bodies wait until that campaign is complete. Issue #225's lifestone/particle alpha comparison remains a separate rendering visual gate.
|
||||
**Status:** Living document. Updated 2026-07-22. **M3 landed; M4 is next after the active `GameWindow` structural prerequisite.** M3's retail casting/UI, R6 locomotion/collision/projectile/teleport/radar rebaseline, deterministic fresh-login/portal world lifecycle, and final two-client portal observer flow are user-gated. The current program is the behavior-preserving ownership campaign in [`docs/architecture/code-structure.md`](../architecture/code-structure.md); Slices 1–7 and Slice 8 checkpoints A–G are complete, with the remaining composition/shutdown checkpoints active. New M4 quest/emote/character-creation feature bodies wait until that campaign is complete. Issue #225's lifestone/particle alpha comparison remains a separate rendering visual gate.
|
||||
**Purpose:** One source of truth for where the project is and where it's going. Every observed defect or missing feature has a named phase that owns it; when something looks wrong in-game, look here to find the phase that'll address it. Implementation details live in per-phase specs under `docs/superpowers/specs/`, not in this file.
|
||||
|
||||
---
|
||||
|
|
@ -79,7 +79,7 @@ second synchronized soak pass with graceful exits, and the six stable PNG
|
|||
checkpoints preserve Slice 6 presentation. Issue #232 tracks the coarse
|
||||
process-residency gate's diagnostic blind spot; no tolerance was loosened.
|
||||
|
||||
Final Slice 8 composition/shutdown cleanup is active. Checkpoints A–F now own
|
||||
Final Slice 8 composition/shutdown cleanup is active. Checkpoints A–G now own
|
||||
the frozen shell boundary, all nine native callback edges, live-session
|
||||
reset/selection/entry/route composition, and world clock/sky/day/weather/
|
||||
AdminEnvirons state. Checkpoint E adds reversible, transactional Silk,
|
||||
|
|
@ -91,8 +91,13 @@ fields / 65 methods. Checkpoint F adds the sole gameplay action-priority
|
|||
subscriber, typed combat/diagnostic/general commands, and a reversible
|
||||
retained-root item-drop binding. `GameWindow` is now 4,057 lines / 198 fields /
|
||||
54 methods; the Checkpoint F Release suite passes 7,524 tests / 5 skips.
|
||||
Settings, startup/resource transfer, shutdown, soak, and closeout checkpoints
|
||||
G–L remain.
|
||||
Checkpoint G adds the pre-window `RuntimeSettingsController`, one immutable
|
||||
startup snapshot, ordered startup pacing/display/FOV/audio application, late
|
||||
runtime-target binding without replay, and one current/toon settings owner.
|
||||
`GameWindow` is now 3,663 lines / 162 fields / 37 methods. Resource transfer,
|
||||
ordered composition, shutdown, soak, and closeout checkpoints H–L remain. The
|
||||
Checkpoint G Release suite passes 7,553 tests / 5 intentional skips, and all
|
||||
three corrected-diff reviews are clean.
|
||||
|
||||
This is a behavior-preserving structural program. Severe regressions still get
|
||||
root-cause fixes in separate commits; ordinary feature work resumes with M4
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ diagnostic owners preserve the accepted draw/failure graph. `GameWindow` is
|
|||
campaign baseline. The full Release suite passes 7,341 tests / 5 skips; the
|
||||
315.6-second capped/reconnect lifecycle gate and 395.2-second synchronized
|
||||
nine-destination soak pass with graceful exits, and six stable PNG checkpoints
|
||||
preserve Slice 6 presentation. Final Slice 8 checkpoints A–F are complete:
|
||||
preserve Slice 6 presentation. Final Slice 8 checkpoints A–G are complete:
|
||||
native callbacks and live-session composition now have explicit retryable
|
||||
owners. Checkpoint D adds the sole world-environment owner for clock, DAT sky,
|
||||
day group, weather, and AdminEnvirons state. Checkpoint E adds terminal,
|
||||
|
|
@ -47,10 +47,13 @@ transactional ownership for Silk/dispatcher/retained/devtools input, the raw
|
|||
camera pointer, focus, and physical framebuffer size. Graceful live-session
|
||||
retirement now precedes physical callback removal. Checkpoint F adds the sole
|
||||
gameplay action-priority owner, typed combat/diagnostic/general commands, and a
|
||||
reversible retained-root item-drop binding. `GameWindow` is 4,057 lines / 198
|
||||
fields / 54 methods; 7,524 Release tests pass / 5 skip. Checkpoints G–L remain
|
||||
active. Issue #232 tracks process-residency variance in the soak without
|
||||
loosening its leak threshold.
|
||||
reversible retained-root item-drop binding. Checkpoint G adds the sole
|
||||
pre-window/runtime settings owner, one startup snapshot, ordered one-shot
|
||||
startup application, and inert late target binding. `GameWindow` is 3,663
|
||||
lines / 162 fields / 37 methods. Checkpoints H–L remain active. Issue #232
|
||||
tracks process-residency variance in the soak without loosening its leak
|
||||
threshold. The Checkpoint G Release suite passes 7,553 tests / 5 skips and all
|
||||
three corrected-diff reviews are clean.
|
||||
|
||||
Carried:
|
||||
#153 far-teleport residual, #116 slide-response, the remaining R6 ownership cleanup plus
|
||||
|
|
|
|||
|
|
@ -0,0 +1,132 @@
|
|||
# GameWindow Slice 8 — Checkpoint G Runtime Settings Plan
|
||||
|
||||
## Objective
|
||||
|
||||
Replace `GameWindow`'s duplicated pre-window and `OnLoad` settings paths with
|
||||
one two-phase `RuntimeSettingsController`. The controller owns persistence and
|
||||
live settings state; render, window, audio, UI, and streaming objects remain
|
||||
borrowed targets. This is a structural cutover, not a redesign of the settings
|
||||
format or retail option behavior.
|
||||
|
||||
Two carried behaviors are now explicit rather than accidental. Saved FOV is
|
||||
applied during startup even when developer tools are disabled; previously it
|
||||
was incorrectly gated on construction of `SettingsVM`. The named-retail
|
||||
`/framerate` live toggle and notice remain intact, while acdream's already
|
||||
shipped cross-launch ShowFps persistence is documented as AP-121 rather than
|
||||
being attributed to the retail command body.
|
||||
|
||||
## Frozen behavior and ordering
|
||||
|
||||
1. Construct the controller before `Window.Create` and load Display, Audio,
|
||||
Gameplay, Chat, and the `default` Character bag exactly once.
|
||||
2. Resolve the preset plus environment overrides once for the immutable startup
|
||||
snapshot. `WindowOptions.VSync` comes from the pacing policy initialized with
|
||||
that snapshot; `WindowOptions.Samples` comes from the same resolved quality.
|
||||
3. After window/GL input, camera, DAT effects, and optional audio exist, but
|
||||
before devtools or world/render factories, apply startup settings in this
|
||||
order: monitor-aware pacing, resolution/fullscreen, field of view, then audio.
|
||||
4. Downstream terrain, dispatcher, render-range, and streaming factories read
|
||||
the same startup quality snapshot. The legacy startup stream-radius override
|
||||
remains at its current composition boundary.
|
||||
5. Bind one complete `RuntimeSettingsTargets` only after window, UI (when
|
||||
enabled), terrain atlas, dispatcher, render-range, and streaming exist.
|
||||
Binding performs no display, quality, UI-lock, or audio replay.
|
||||
6. Settings-panel Save preserves its callback order: keybindings, Display,
|
||||
Audio, Gameplay, Chat, Character. Each section retains its existing
|
||||
persistence/error boundary.
|
||||
7. Display Save persists first, applies resolution/fullscreen, publishes the
|
||||
new display snapshot, then reapplies quality. A changed MSAA sample count is
|
||||
logged as restart-required and is not applied to the live GL context.
|
||||
8. Runtime quality reapply preserves the existing order: alpha-to-coverage,
|
||||
terrain anisotropy, render-range publication, streaming reconciliation,
|
||||
completion budget.
|
||||
9. `/framerate`, UI lock, loot permits, and combat preferences mutate the
|
||||
controller's canonical state, synchronize the optional Settings draft using
|
||||
the existing draft-preservation rules, and retain their existing save-error
|
||||
behavior.
|
||||
10. Enter-world changes the active toon key, loads that character bag even when
|
||||
devtools are disabled, and publishes it to the optional Settings view model.
|
||||
Session reset restores the startup/default character context before the
|
||||
later identity-reset operation restores the key to `default`.
|
||||
11. Per-frame display/audio preview reads the optional Settings draft through a
|
||||
typed source. Particle range and FPS visibility read the same source so an
|
||||
unsaved draft still previews exactly as it does today.
|
||||
12. Shutdown first withdraws the Settings view-model and runtime-target loans;
|
||||
the controller never disposes the window, renderer, UI, streaming, audio, or
|
||||
input objects it borrows.
|
||||
|
||||
## Types and ownership
|
||||
|
||||
- `IRuntimeSettingsStorage` is the test seam for the five settings bags.
|
||||
`JsonRuntimeSettingsStorage` is the production owner of the one concrete
|
||||
`SettingsStore` and exposes that store only for retained-window layout
|
||||
persistence.
|
||||
- `RuntimeSettingsSnapshot` is the immutable startup value.
|
||||
- `IRuntimeSettingsStartupTarget` receives the one startup Display/Audio apply.
|
||||
- `IRuntimeSettingsTargets` receives future display-window, quality, and UI-lock
|
||||
changes. `BindRuntimeTargets` stores it without invoking it.
|
||||
- `IRuntimeSettingsPreviewSource` exposes current Display/Audio preview values
|
||||
and whether a live draft exists.
|
||||
- `RuntimeSettingsController` owns persistence, current values, active toon,
|
||||
resolved quality, and the optional `SettingsVM` binding. It also implements
|
||||
the combat settings source; no second gameplay-state mirror remains.
|
||||
- `SilkRuntimeDisplayWindowTarget`, `RuntimeSettingsStartupTargets`, and
|
||||
`RuntimeSettingsTargets` are App-layer adapters over borrowed runtime objects.
|
||||
|
||||
## Automated gates
|
||||
|
||||
- Construction loads every bag once and populates one immutable snapshot.
|
||||
- Startup apply is ordered, exactly once, and independent of GL in controller
|
||||
tests.
|
||||
- Runtime target binding produces zero calls; unbinding prevents future target
|
||||
calls while state and persistence still advance.
|
||||
- Display Save ordering, quality transition, and restart-required MSAA logging.
|
||||
- Quality target receives one complete resolved value per reapply.
|
||||
- Draft preview/cancel, external FPS mutation, UI lock, loot permits, and combat
|
||||
option synchronization.
|
||||
- Toon activate/load/reset/save behavior with and without a Settings view model.
|
||||
- Save failures preserve each established state/target boundary.
|
||||
- Source-boundary test proves `GameWindow` no longer constructs or loads a
|
||||
`SettingsStore`, owns persisted settings fields, or contains quality/display
|
||||
feature bodies.
|
||||
- Focused App tests, full App tests, Release solution build, and full Release
|
||||
suite.
|
||||
|
||||
## Review and commit gate
|
||||
|
||||
After the focused tests pass, the existing retail-conformance,
|
||||
architecture/integration, and adversarial reviewers inspect the complete diff
|
||||
in parallel. Confirmed findings are corrected and the same reviewers repeat
|
||||
until clean. Documentation, roadmap, issues, memory, `CLAUDE.md`, and
|
||||
`AGENTS.md` are reconciled in the same bisectable Checkpoint G commit.
|
||||
|
||||
## Implementation result
|
||||
|
||||
- `RuntimeSettingsController` is constructed before `Window.Create`; all five
|
||||
bags load once and `WindowOptions` consumes its immutable startup snapshot.
|
||||
- Startup substeps commit independently, so an audio failure retries audio
|
||||
without replaying already successful pacing/display/FOV work.
|
||||
- Late target binding is inert and reversible; expected-instance SettingsVM
|
||||
withdrawal cannot detach a replacement binding.
|
||||
- The concrete quality adapter preserves all five application steps and the
|
||||
unchanged MSAA restart boundary.
|
||||
- Combat changes merge their three fields into a live Gameplay draft rather
|
||||
than overwriting unrelated unsaved fields; successful external changes also
|
||||
advance the SettingsVM persisted baseline so Cancel cannot resurrect stale
|
||||
command state.
|
||||
- UI-lock target, persistence, and baseline publication form one explicit
|
||||
convergence state. A transient failure leaves the same requested value
|
||||
retryable instead of letting the equality fast-path strand unfinished work.
|
||||
- Enter/reset/toon changes load and publish Character state independently of
|
||||
developer-tool availability.
|
||||
- `GameWindow` no longer constructs or loads `SettingsStore`, owns persisted
|
||||
settings mirrors, or contains display/quality/settings feature bodies.
|
||||
- Candidate metrics: 3,663 raw lines / 162 fields / 37 methods, down 394 lines /
|
||||
36 fields / 17 methods from Checkpoint F and 12,060 lines (76.7%) from the
|
||||
campaign baseline.
|
||||
- Thirty-five focused App settings/boundary tests, all 43 `SettingsVMTests`, the
|
||||
UI Abstractions Release suite (534 pass), and the App Release suite (3,183
|
||||
pass / 3 intentional skips) pass. All three independent corrected-diff
|
||||
reviews are clean. The production App Release build has zero warnings/errors;
|
||||
the solution Release build retains the 17 existing #228 test-project warnings;
|
||||
and the complete Release suite passes 7,553 tests / 5 intentional skips.
|
||||
|
|
@ -25,7 +25,7 @@ audit.
|
|||
resize behind symmetric named subscriptions.
|
||||
- [x] F — extract the sole gameplay input-action router plus focused combat and
|
||||
diagnostic command owners.
|
||||
- [ ] G — extract two-phase persisted settings/display/quality ownership.
|
||||
- [x] G — extract two-phase persisted settings/display/quality ownership.
|
||||
- [ ] H — give terrain atlas, sky shader, retained `UiHost`, and both frame roots
|
||||
explicit single ownership and transfer seams.
|
||||
- [ ] I — group `OnLoad` into small ordered, fakeable composition phases with
|
||||
|
|
@ -557,6 +557,29 @@ fields / 54 methods.
|
|||
- Preserve restart-required quality behavior and test transitions/previews
|
||||
without requiring GL.
|
||||
|
||||
**Implementation result:** one pre-window `RuntimeSettingsController` now owns
|
||||
the concrete settings store, the immutable startup snapshot, current Display /
|
||||
Audio / Gameplay / Chat / Character values, the active toon, resolved quality,
|
||||
and the optional Settings draft. Startup applies pacing, window state, saved
|
||||
FOV, and audio in order exactly once; a failed later substep retries without
|
||||
replaying a successful earlier substep. Complete runtime targets bind only
|
||||
after their borrowers exist and binding performs no replay. Display saves keep
|
||||
the persistence → live window → snapshot → quality order; quality applies
|
||||
alpha-to-coverage → anisotropy → render range → streaming → completion budget.
|
||||
Combat preference changes merge only their three fields into a live draft, so
|
||||
unrelated unsaved Gameplay edits survive. Saved FOV now applies without
|
||||
devtools, correcting the old accidental SettingsVM gate. `/framerate` retains
|
||||
the named-retail live toggle/notice and keeps acdream's shipped cross-launch
|
||||
persistence as documented AP-121. UI-lock convergence requires target,
|
||||
persistence, and Settings baseline publication; a failed substep keeps the
|
||||
same-value command retryable. `GameWindow` is 3,663 raw lines / 162 fields / 37
|
||||
methods. Thirty-five focused App settings/boundary tests, all 43
|
||||
`SettingsVMTests`, the UI Abstractions Release suite (534 pass), and the App
|
||||
Release suite (3,183 pass / 3 intentional skips) pass. All three independent
|
||||
corrected-diff reviews are clean; the production App Release build has zero
|
||||
warnings/errors, and the complete Release suite passes 7,553 tests / 5
|
||||
intentional skips (17 existing test-project warnings remain tracked by #228).
|
||||
|
||||
### H — explicit single resource ownership and frame slots
|
||||
|
||||
- Publish TerrainAtlas and the dedicated sky Shader as separate lifetime roots;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue