Add emergency aftermath: evacuation, investigation, review copy
Full build / Import + headless tests (push) Successful in 26s
Full build / Full desktop build + optional release (push) Failing after 4m20s

- Responder outcomes now reach the shift review
  (ShiftCoordinator.responder_outcomes), and the review screen names them.
- "evacuation" (emergency call, low danger, no weapon) actually clears the entrance:
  the door is locked, every NPC flees and is marked as leaving, and a
  security_failure reputation hit applies.
- An emergency call the situation did not justify (no weapon, danger <= 1) appends
  an investigation note, records investigation_opened, and applies the existing
  false_report hit. The review lists the investigations.
- Fix dispatch dying after the first shift: coordinator.setup() builds a new
  RadioSystem, so the responder_arrived connection made in _ready was lost on every
  venue switch/restart. _connect_radio() re-wires it beside _connect_crowd().

Tests/docs
- Headless suite 105 -> 113 (test_emergency_aftermath.gd), new smoke_emergency.gd
  covering the investigation, evacuation aftermath, and review copy.
- README controls/status/smoke checklist, TODO section moved to DONE, MEMORY notes.
- Version 0.2.5.
This commit is contained in:
zwitschi committed 2026-10-31 20:59:06 +01:00
1 parent 71b0b53705
commit 921bab796e
25 files changed
+1019 -23

No files matched your search

+22 -2
View File
@@ -21,8 +21,8 @@ Session memory for durable decisions, state, and gotchas. Keep concise, remove o
Windowed control smoke: `godot --path . --script res://src/test/smoke_focus_radial.gd` → exit 0.
- `main` is in sync with origin. **v0.2.2** tags the session-shell + world-follow-up commit;
CI builds the portable binaries, NSIS installer, and AppImage on the tag push.
- Next work: `TODO.md` emergency aftermath (evacuation, unjustified-call investigation), then
body-camera replay timeline and NPC theater poses.
- Next work: `TODO.md` body-camera replay timeline, then NPC theater poses (sit/photo/perform)
and audio.
- Do not re-open `override_access`. Do not bind wand to `W`. Do not remove the radio easter egg.
## Current State
@@ -94,6 +94,15 @@ Session memory for durable decisions, state, and gotchas. Keep concise, remove o
`_begin_incident()` now starts one per focused NPC (`has_open_incident()` guard), verbs call
`_ensure_incident()`, and `ShiftCoordinator._finish_shift()` closes leftovers as `unresolved`
before building the review.
- **Radio dispatch was dead after the first shift:** `coordinator.setup()` builds a new
`RadioSystem`, so the `responder_arrived` connection made in `_ready` was lost on every venue
switch/restart (responders never resolved anything). `_connect_radio()` now re-wires it next to
`_connect_crowd()` after every setup. Same class of bug as the crowd signal.
- **Emergency aftermath:** `ShiftCoordinator.responder_outcomes` / `investigations` feed the review.
`evacuation` (emergency call, low danger, no weapon) locks the door, makes every NPC flee, marks
them `leave_requested`, and applies a `security_failure` hit. An emergency placed while
`current_npc_truth` has no weapon and `danger_level <= 1` appends an investigation note, records
`investigation_opened`, and applies `false_report` -6.
- **Skyline backdrop (2026-10-31):** `PlaneMesh` defaults to a **horizontal** XZ plane — set
`mesh.orientation = PlaneMesh.FACE_Z` or the "backdrop" renders as a band overhead. The skyline
is now a ring of four 400x60 planes at 200 m (center y=30, so building bases meet the ground),
@@ -192,6 +201,15 @@ Session memory for durable decisions, state, and gotchas. Keep concise, remove o
- NOTE: collaborators occasionally add uncommitted work to this shared tree (e.g. the radio
easter egg); check `git status` before committing and leave foreign changes untouched unless asked.
- Screen-design references (`tools/screen_designs.py`, tests in `tools/test_screen_designs.py`):
`generate` turns the screen descriptions in `docs/` (README captions, ADRs 0007–0010,
PLAN, architecture) into reference images under `docs/screens/designs/` — `--draft`
draws offline Pillow wireframes, `--ai` generates OpenRouter mockups (default model
`openai/gpt-5-image-mini`). `compare` checks `docs/screenshots/*.png` for aspect/size/
blank-frame and coarse layout/palette/detail drift. Drift distances are warnings, not
failures: a mockup never matches a real render, so semantic composition is a follow-up
vision-model judge (tracked in TODO).
## Known Issues / Notes
- Reference cycles are fixed: `FSM` holds its owner via `WeakRef`, `ShiftCoordinator` is
@@ -222,6 +240,8 @@ Session memory for durable decisions, state, and gotchas. Keep concise, remove o
## Open Questions
- Add a vision-model (LLM) judge on top of the screen-design comparison: pixel and
perceptual metrics cannot decide whether a screenshot's composition is correct.
- Whether the responder avatar should be playable/controllable or purely scripted.
- Localization target languages beyond English.
- macOS notarization approach for broad distribution.