feat(map): settlement (city/town) map site + generator - #319
Merged
Conversation
Adds a Settlement map site parallel to DungeonSite — the P1 slice of the map-hierarchy epic (city/town generator). A settlement holds a flat list of buildings and can be anchored to a world hex. - Model: Building + SettlementSite; MapState.settlements/activeSettlementId (reuses juice.map.v1, JSON omitted when empty -> legacy byte-stable). - Oracle: settlementName()/buildingType() over the existing authored settlement_* tables (no new data rail, facts-only). - MapNotifier: generateSettlement (name + N buildings), add/switch/rename/ kind/note/remove, anchor/unanchor, and building CRUD. - UI: a new Maps -> Town subtab (settlement_pane.dart) with a switcher, Generate town / New, rename+kind editor, hex anchoring, and a building list with add/edit/delete. Cross-nesting (building -> dungeon), a hex-card "Town here" chip, and richer town tables are deferred to P2/P3 — see the design doc. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The subtab host keeps every pane mounted and measures the off-screen ones under unbounded width, where Material text buttons assert "forces an infinite width" (the documented tool-host loose-constraint gotcha). This crashed unrelated shell tests once the Town pane joined the maps stack. Bound the pane width via a LayoutBuilder and use fixed-size IconButtons (immune) for the Generate/New header actions. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
P1 of the map-hierarchy epic — a city/town generator as a first-class map site (parallel to
DungeonSite).Building+SettlementSite;MapState.settlements/activeSettlementId(reusesjuice.map.v1, JSON omitted when empty → legacy byte-stable).settlementName()/buildingType()over the existing authoredsettlement_*tables (no new data rail, facts-only).MapNotifier):generateSettlement(name + N buildings), add/switch/rename/kind/note/remove, anchor/unanchor to a hex, building CRUD.settlement_pane.dart) — switcher, Generate town / New, rename+kind editor, hex anchoring, building list with add/edit/delete.Cross-nesting (building → dungeon), a hex-card "Town here" chip, and richer town tables are deferred to P2/P3 — see
docs/superpowers/specs/2026-07-21-settlement-map-generator-design.md.Gotcha fixed: the subtab host measures off-screen panes under unbounded width; the header uses fixed-size IconButtons (immune) + a LayoutBuilder width bound so Material text buttons don't assert.
Test plan
settlement_test.dart(model + notifier),settlement_pane_test.dart(widget), maps_tab Town assertion🤖 Generated with Claude Code