docs(@projects/@magic-civilization): 📋 reopen Game-1 scope — 6 verified gap objectives (p3-19..24)

Game 1 was NOT actually complete; the green dashboard overstated it. Created
objectives for the verified, untracked gaps (all confirmed 2026-06-25 against the
code, both Rust + GDScript paths):
- p3-19 player→ecology feedback (over-harvest/hunt deplete live populations; extinction)
- p3-20 weather affects scouting (vision penalty, not just movement)
- p3-21 weather-driven migration (migration ignores weather today)
- p3-22 AI builds dedicated scouts (only frontier-seeks with idle military)
- p3-23 trade richness (luxury swaps only; no gold/strategic trades)
- p3-24 Rail-1 port of economy/happiness/climate per-turn glue logic from GDScript

Dashboard regenerated. (Systems I'd wrongly doubted — ecology engine ticking, AI
worker improvements, naval harbor-gating — are confirmed working; not reopened.)

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Natalie 2026-06-25 13:45:20 -04:00
parent 58b608804a
commit ed3c836e2f
8 changed files with 333 additions and 7 deletions

View file

@ -17,8 +17,8 @@
| **P0** | 44 | 0 | 0 | 0 | 0 | 0 | 44 |
| **P1** | 88 | 0 | 0 | 0 | 0 | 1 | 89 |
| **P2** | 130 | 0 | 0 | 0 | 0 | 1 | 131 |
| **P3 (oos)** | 29 | 0 | 0 | 0 | 0 | 29 | 58 |
| **total** | **291** | **0** | **0** | **0** | **0** | **31** | **322** |
| **P3 (oos)** | 29 | 0 | 3 | 0 | 3 | 29 | 64 |
| **total** | **291** | **0** | **3** | **0** | **3** | **31** | **328** |
</td><td valign='top' style='padding-left:2em'>
@ -26,7 +26,7 @@
| Team Lead | Remaining |
|---|---|
| — | 0 |
| [warcouncil](../team-leads/warcouncil.md) | 6 |
</td></tr></table>

View file

@ -0,0 +1,52 @@
---
id: p3-19
title: Player → ecology feedback — harvesting & hunting deplete live populations (over-harvest → extinction)
priority: p3
status: missing
scope: game1
owner: warcouncil
updated_at: 2026-06-25
---
## Summary
The living-world ecology sim (mc-ecology / mc-worldsim) ticks per played turn
(populations grow/collapse, migrate, emerge — see g2-08/g2-10, all done), and the
player can harvest flora (chop, `mc-city::harvest`) and kill fauna (combat /
lair clearing, `mc-combat::loot`). **But the two are decoupled:** harvesting and
hunting do NOT reduce the ecology `PopulationSlot::population`
(`mc-ecology/src/population.rs:9`) — fauna products are a read-only yield
(`fauna_product.rs`), and chopping flips terrain + grants a one-shot yield without
touching the live population. Only the sim's own tier dynamics cut populations
(`evolution.rs:1119 ecological_t5_reduces_fauna_populations`).
Net: **you cannot over-harvest or over-hunt a species toward local extinction**,
and abundance doesn't respond to player pressure — which undercuts the
"living-world is the Game-1 USP" promise (the world should react to the player).
## Acceptance
- [ ] Killing fauna (combat / lair clear) decrements that species' live
`PopulationSlot::population` on/near the tile (scaled by group size killed).
- [ ] Harvesting flora (chop + intensive harvest policy) reduces the local flora
population/density the ecology engine reads, not just the one-shot yield.
- [ ] Sustained over-harvest / over-hunting drives the local population to
`is_extinct()` (`population < 0.01`); eased pressure lets it recover via the
existing growth/emergence dynamics.
- [ ] Logic lives in Rust (the coupling is in mc-ecology / mc-turn, not GDScript).
- [ ] Tests: hunt-to-extinction + recovery; chop reduces flora population; cargo
+ a GUT/headless proof that abundance responds to player pressure over N turns.
## Code sites
- `mc-ecology/src/population.rs` (population mutation API — add a depletion method)
- `mc-ecology/src/fauna_product.rs` (currently read-only yield)
- `mc-combat/src/loot.rs` + the kill path (decrement on kill)
- `mc-city/src/harvest.rs` / `harvest_policy.rs` (chop / intensive → population)
- the per-turn coupling site (mc-turn or the worldsim tick driver)
## Notes
Verified 2026-06-25 (this is a genuine gap, not a wrongly-marked-done objective).
The ecology engine itself IS wired into the played turn (`turn_manager.gd:302`
`mc-worldsim`); what's missing is the player→population coupling.

View file

@ -0,0 +1,42 @@
---
id: p3-20
title: Weather affects scouting — vision/LoS penalty under storms, blizzards, dust
priority: p3
status: missing
scope: game1
owner: warcouncil
updated_at: 2026-06-25
---
## Summary
The runtime weather system (`mc-climate::weather`, six Game-1 types: Storm, Heat
Wave, Blizzard, Drought, Flood, Dust Storm) derives events per turn and applies a
`movement_penalty` to units, with real unit HP damage wired into the played turn
(`climate_effects.gd:125`). **But `WeatherEvent` carries no vision/line-of-sight
effect** — weather slows movement and hurts units, but does not reduce scouting
range. So storms/blizzards/dust have no effect on exploration, fog reveal, or
surprise — a missed gameplay lever for the weather system.
## Acceptance
- [ ] `mc-climate::weather::WeatherEvent` gains a `vision_penalty` (per type;
authored in the weather thresholds JSON, data-driven).
- [ ] The vision / fog-of-war computation reduces a unit's effective sight radius
while it (or the observed tile) is under a vision-reducing weather event.
- [ ] Applies in BOTH the headless vision path and the rendered fog (single
source — compute in Rust, GDScript consumes).
- [ ] Surfaced to the player (reduced reveal under weather is observable).
- [ ] Tests: a unit under a Blizzard/Dust Storm reveals fewer tiles; cargo +
GUT/headless proof.
## Code sites
- `mc-climate/src/weather.rs` (`WeatherEvent` + thresholds)
- the vision computation (`mc-vision` / `PlayerVision`; `pathfinder.gd::visible_hexes`
+ the Rust vision projection)
- `public/resources/.../weather*.json` (per-type vision_penalty authoring)
## Notes
Verified 2026-06-25 — weather is `movement_penalty`-only; no vision field exists.

View file

@ -0,0 +1,40 @@
---
id: p3-21
title: Weather/climate-driven fauna & flora migration
priority: p3
status: partial
scope: game1
owner: warcouncil
updated_at: 2026-06-25
---
## Summary
Fauna/flora migration EXISTS and ticks per played turn
(`mc-ecology/src/biological.rs:59 MigrationPulse`, `engine.rs` per-turn migration;
g2-10 done), but it is **population-pressure / carrying-capacity driven only**
it does not respond to **weather/climate**. Drought should push herds toward
water, blizzards/heat-waves should thin or relocate populations, blooms (already
climate-linked) should pull flora spread. Today the living world migrates by
crowding, not by climate — a partial realization of the weather↔ecology coupling.
## Acceptance
- [ ] Weather/climate events bias migration triggers and/or destinations
(e.g. drought raises migration-trigger chance + steers toward wetter tiles;
blizzard reduces local carrying capacity → emigration).
- [ ] Coupling is data-driven (per-weather migration modifiers authored in JSON,
not hardcoded).
- [ ] Logic in Rust (mc-ecology consumes the weather layer); GDScript only ticks.
- [ ] Tests: a drought shifts migration vs. a calm baseline (deterministic).
## Code sites
- `mc-ecology/src/biological.rs` (`MigrationPulse`, migration trigger/targeting)
- `mc-ecology/src/engine.rs` (per-turn migration step)
- `mc-climate::weather` (the weather layer to consume)
## Notes
Verified 2026-06-25 — migration is pop-pressure-driven; weather does not influence it.
Status `partial`: migration works, the weather-driving is the missing half.

View file

@ -0,0 +1,40 @@
---
id: p3-22
title: AI builds dedicated scout units for exploration
priority: p3
status: missing
scope: game1
owner: warcouncil
updated_at: 2026-06-25
---
## Summary
The AI explores via frontier-seek with idle military units
(`mc-ai/src/tactical/movement.rs:892`) and gives scout-typed units a special
enemy-city patrol sweep — but it **never builds `dwarf_scout`**: the production
ladder (`mc-ai/src/tactical/production.rs:387`) queues founders, military, and
buildings, with workers as fallback, and no scout branch. Early-game discovery /
first-contact therefore relies on diverting combat units, which is slower and
weaker than a cheap dedicated scout.
## Acceptance
- [ ] `production.rs` queues a `dwarf_scout` early (e.g. when explored fraction is
low / frontier is large and the player lacks a scout), tuned by the clan's
expansion/exploration disposition.
- [ ] The built scout actually feeds exploration (frontier-seek / first-contact)
faster than the idle-military baseline.
- [ ] Logic in `mc-ai` (Rust). Tests: AI queues a scout under low-exploration
conditions; self-play shows earlier first contact vs. the no-scout baseline.
## Code sites
- `mc-ai/src/tactical/production.rs` (production priority ladder)
- `mc-ai/src/tactical/movement.rs` (scout sweep + frontier-seek already exist)
- `public/resources/units/dwarf_scout.json`
## Notes
Verified 2026-06-25. Minor relative to the ecology/weather gaps, but a real AI
quality gap (the AI under-explores in the opening).

View file

@ -0,0 +1,41 @@
---
id: p3-23
title: Trade richness — gold & strategic-resource trades with opponents
priority: p3
status: partial
scope: game1
owner: warcouncil
updated_at: 2026-06-25
---
## Summary
Inter-player trade EXISTS but is **luxury-for-luxury swaps only**
(`mc-trade/src/lib.rs:139 evaluate_trades`; AI-driven, relation-gated, can't trade
your last copy). You **cannot trade gold or strategic resources** with opponents,
and the `tribute.rs` path is deferred to Game 2. That makes diplomacy/economy
thinner than the resource model implies (strategic resources gate units and are
tradeable in concept, but no exchange path exists).
## Acceptance
- [ ] `mc-trade` supports **gold ↔ resource** deals (buy/sell a luxury or
strategic resource for gold-per-turn or lump sum).
- [ ] `mc-trade` supports **strategic-resource** trades (e.g. iron for horses),
with the same "keep your last copy" protection.
- [ ] AI evaluates and proposes/accepts these deals (willingness + relation +
need, reusing the existing evaluation surface).
- [ ] Logic in Rust (`mc-trade`); GDScript only surfaces the deal UI. Tests:
gold-for-luxury and strategic-for-strategic deals evaluate + activate.
## Code sites
- `mc-trade/src/lib.rs` (`evaluate_trades`, `TradeAgreement`, `TradeLedger`)
- `mc-trade/src/tribute.rs` (deferred path — keep Game-2 gated)
- `public/resources/resources.json` (strategic `tradeable` flags)
## Notes
Verified 2026-06-25. Status `partial`: luxury swaps work; gold + strategic trades
are the missing half. (Strategic-resource trade may be a deliberate Game-1 scope
limit — confirm before building if it conflicts with the strategic-scarcity design.)

View file

@ -0,0 +1,51 @@
---
id: p3-24
title: Rail-1 — port per-turn economy/happiness/climate glue logic from GDScript to Rust
priority: p3
status: partial
scope: game1
owner: warcouncil
updated_at: 2026-06-25
---
## Summary
The core economy/happiness/event MATH is in Rust (mc-economy, mc-happiness,
mc-city, mc-climate, mc-trade) — good Rail-1 health. **But real per-turn game
logic still lives in GDScript**, violating "GDScript is presentation only":
- `economy.gd:66-72` computes gold *in GDScript* (building-gold sum, gold-per-pop,
gold-from-mines) before/around the `GdEconomy` call — not a thin wrapper.
- `happiness.gd` assembles + partially computes the happiness inputs (luxury map,
building-effect collection) in GDScript.
- `climate_effects.gd:125` mutates game state in GDScript (`unit.hp -= hp_loss`).
- `turn_processor.gd` / `turn_manager.gd` own the per-turn ORCHESTRATION (sequence
the Rust crates, dispatch events, apply results) in GDScript.
This is the same class of debt as the AI port (p0-26, done) — but for the
economy/happiness/event/turn surface.
## Acceptance
- [ ] Gold income/expense aggregation (incl. per-pop, per-mine, building sums)
computed entirely in `mc-economy` from state; `economy.gd` only passes state +
applies the result.
- [ ] Happiness input assembly + computation fully in `mc-happiness`; `happiness.gd`
reduced to a thin bridge.
- [ ] Climate-effect damage application (unit HP loss) owned by Rust; GDScript
renders/animates only.
- [ ] (Stretch) per-turn orchestration moved behind a Rust turn driver so the
GDScript turn loop is a thin pump (overlaps the broader pathfinder/turn port).
- [ ] No regression: cargo + canonical GUT suite green.
## Code sites
- `src/game/engine/src/modules/empire/economy.gd``mc-economy`
- `src/game/engine/src/modules/empire/happiness.gd``mc-happiness`
- `src/game/engine/src/modules/climate/climate_effects.gd``mc-climate`/`mc-turn`
- `src/game/engine/src/modules/management/turn_processor.gd` (orchestration)
## Notes
Verified 2026-06-25. Phased / can land incrementally per surface. Related: p0-26
(AI port, done), the standing pathfinder.gd port debt (p3-18 P5b note).

View file

@ -1,13 +1,13 @@
{
"generated_at": "2026-06-25T11:28:51Z",
"generated_at": "2026-06-25T17:45:19Z",
"totals": {
"partial": 3,
"oos": 31,
"done": 291,
"stub": 0,
"partial": 0,
"in_progress": 0,
"missing": 0,
"total": 322
"missing": 3,
"total": 328
},
"objectives": [
{
@ -3229,6 +3229,66 @@
"owner": "warcouncil",
"updated_at": "2026-06-25",
"summary": "Land armies are permanently confined to their starting landmass: `mc-pathfinding`\ngates water purely by `UnitDomain` (`is_passable(\"ocean\", Land)` is hard-`false`),\nwith no tech override and no way to embark or be ferried. On maps where the two\ncapitals sit on separate landmasses (common — the start-balancer maximally\nseparates capitals on the 40×24 `duel` map, often ocean-separated), conquest by a\nland army is impossible. This is the Civ \"embarkation\" tech gap.\n\nThe scaffolding is **half-built** (existing tech debt): `mc_combat::siege::\nembarked_defence_penalty` (halves an embarked unit's defence — the Civ-V/VI\nvulnerability rule) and a `transport` keyword in `combat.json` (\"carry up to 2\nland units across water\", on `dwarf_fortress_ship`) both exist, but neither is\nwired into movement/pathfinding, so they are dead."
},
{
"id": "p3-19",
"title": "Player → ecology feedback — harvesting & hunting deplete live populations (over-harvest → extinction)",
"priority": "p3",
"status": "missing",
"scope": "game1",
"owner": "warcouncil",
"updated_at": "2026-06-25",
"summary": "The living-world ecology sim (mc-ecology / mc-worldsim) ticks per played turn\n(populations grow/collapse, migrate, emerge — see g2-08/g2-10, all done), and the\nplayer can harvest flora (chop, `mc-city::harvest`) and kill fauna (combat /\nlair clearing, `mc-combat::loot`). **But the two are decoupled:** harvesting and\nhunting do NOT reduce the ecology `PopulationSlot::population`\n(`mc-ecology/src/population.rs:9`) — fauna products are a read-only yield\n(`fauna_product.rs`), and chopping flips terrain + grants a one-shot yield without\ntouching the live population. Only the sim's own tier dynamics cut populations\n(`evolution.rs:1119 ecological_t5_reduces_fauna_populations`).\n\nNet: **you cannot over-harvest or over-hunt a species toward local extinction**,\nand abundance doesn't respond to player pressure — which undercuts the\n\"living-world is the Game-1 USP\" promise (the world should react to the player)."
},
{
"id": "p3-20",
"title": "Weather affects scouting — vision/LoS penalty under storms, blizzards, dust",
"priority": "p3",
"status": "missing",
"scope": "game1",
"owner": "warcouncil",
"updated_at": "2026-06-25",
"summary": "The runtime weather system (`mc-climate::weather`, six Game-1 types: Storm, Heat\nWave, Blizzard, Drought, Flood, Dust Storm) derives events per turn and applies a\n`movement_penalty` to units, with real unit HP damage wired into the played turn\n(`climate_effects.gd:125`). **But `WeatherEvent` carries no vision/line-of-sight\neffect** — weather slows movement and hurts units, but does not reduce scouting\nrange. So storms/blizzards/dust have no effect on exploration, fog reveal, or\nsurprise — a missed gameplay lever for the weather system."
},
{
"id": "p3-21",
"title": "Weather/climate-driven fauna & flora migration",
"priority": "p3",
"status": "partial",
"scope": "game1",
"owner": "warcouncil",
"updated_at": "2026-06-25",
"summary": "Fauna/flora migration EXISTS and ticks per played turn\n(`mc-ecology/src/biological.rs:59 MigrationPulse`, `engine.rs` per-turn migration;\ng2-10 done), but it is **population-pressure / carrying-capacity driven only** —\nit does not respond to **weather/climate**. Drought should push herds toward\nwater, blizzards/heat-waves should thin or relocate populations, blooms (already\nclimate-linked) should pull flora spread. Today the living world migrates by\ncrowding, not by climate — a partial realization of the weather↔ecology coupling."
},
{
"id": "p3-22",
"title": "AI builds dedicated scout units for exploration",
"priority": "p3",
"status": "missing",
"scope": "game1",
"owner": "warcouncil",
"updated_at": "2026-06-25",
"summary": "The AI explores via frontier-seek with idle military units\n(`mc-ai/src/tactical/movement.rs:892`) and gives scout-typed units a special\nenemy-city patrol sweep — but it **never builds `dwarf_scout`**: the production\nladder (`mc-ai/src/tactical/production.rs:387`) queues founders, military, and\nbuildings, with workers as fallback, and no scout branch. Early-game discovery /\nfirst-contact therefore relies on diverting combat units, which is slower and\nweaker than a cheap dedicated scout."
},
{
"id": "p3-23",
"title": "Trade richness — gold & strategic-resource trades with opponents",
"priority": "p3",
"status": "partial",
"scope": "game1",
"owner": "warcouncil",
"updated_at": "2026-06-25",
"summary": "Inter-player trade EXISTS but is **luxury-for-luxury swaps only**\n(`mc-trade/src/lib.rs:139 evaluate_trades`; AI-driven, relation-gated, can't trade\nyour last copy). You **cannot trade gold or strategic resources** with opponents,\nand the `tribute.rs` path is deferred to Game 2. That makes diplomacy/economy\nthinner than the resource model implies (strategic resources gate units and are\ntradeable in concept, but no exchange path exists)."
},
{
"id": "p3-24",
"title": "Rail-1 — port per-turn economy/happiness/climate glue logic from GDScript to Rust",
"priority": "p3",
"status": "partial",
"scope": "game1",
"owner": "warcouncil",
"updated_at": "2026-06-25",
"summary": "The core economy/happiness/event MATH is in Rust (mc-economy, mc-happiness,\nmc-city, mc-climate, mc-trade) — good Rail-1 health. **But real per-turn game\nlogic still lives in GDScript**, violating \"GDScript is presentation only\":\n\n- `economy.gd:66-72` computes gold *in GDScript* (building-gold sum, gold-per-pop,\n gold-from-mines) before/around the `GdEconomy` call — not a thin wrapper.\n- `happiness.gd` assembles + partially computes the happiness inputs (luxury map,\n building-effect collection) in GDScript.\n- `climate_effects.gd:125` mutates game state in GDScript (`unit.hp -= hp_loss`).\n- `turn_processor.gd` / `turn_manager.gd` own the per-turn ORCHESTRATION (sequence\n the Rust crates, dispatch events, apply results) in GDScript.\n\nThis is the same class of debt as the AI port (p0-26, done) — but for the\neconomy/happiness/event/turn surface."
}
]
}