rimlike/autoload/strings.gd
megaproxy b9093dd24b Phase 17: Touch UX (PawnDetail+BuildDrawer+WorkMatrix+AlertsLog+Settings)
Three-agent fan-out shipping the major touch UI surfaces. Opus pre-wrote
6 EventBus signals (pawn_selected/deselected, pawn_priority_changed,
alert_added, request_wolf_spawn, day_ended) + Pawn.work_priorities
Dictionary stub before dispatch. Pattern proven across Phases 12-17.

Pawn detail + Settings (Agent A):
- scenes/ui/pawn_detail_panel.gd — right-side CanvasLayer (layer 18),
  ~360px wide, opens on EventBus.pawn_selected. Renders portrait,
  HP/Hunger/Sleep bars with threshold colors, current job, mood +
  sulking, statuses, top 5 mood thoughts, full skill table,
  read-only work-priorities row. Live-refreshes each sim tick.
- scenes/ui/settings_menu.gd — modal CanvasLayer (layer 26), opened
  via Settings button. Auto-pause toggles (Threat/Wanderer/Pawn-Down/
  Modal), audio sliders (stubs for Phase 18), accessibility checkboxes.
  Persists via GameState.apply_settings.
- scenes/world/selection.gd — extended to emit pawn_selected/deselected
  through EventBus on tap.

Build drawer + 12 new Designation tools (Agent B):
- scenes/ui/build_drawer.gd — bottom-sheet CanvasLayer (layer 16) with
  4 tabs (Designate/Build/Stockpile/Cancel) + FAB ⊕ open button.
  Each tab has HFlowContainer of 80×80 buttons with procedural colored
  icons + label. Tap → Designation.set_active_tool + alert + auto-close.
- Designation: added TOOL_CHOP, TOOL_MINE, TOOL_BUILD_CRATE,
  TOOL_BUILD_BED, TOOL_BUILD_TORCH, 5× TOOL_BUILD_WORKBENCH_* variants,
  TOOL_PAINT_STOCKPILE. Plus tool_material override for wall/floor.
- World._on_designation_added: extended dispatch for all 12 new tools;
  added _spawn_workbench() helper for the 5 bench kinds.

Work matrix + Alerts log + Decision refactor + Wolf signal (Agent C):
- scenes/ai/decision.gd: Layer 4 now filters by pawn.work_priorities
  (0=OFF skip, sort by level ascending with provider.priority tiebreak).
  NEEDS_CATEGORIES (rest/eat/sleep) bypass the filter — a pawn can
  never starve from misconfiguration. Audit log prefixes work decisions
  with (pri=N).
- scenes/ui/work_priority_matrix.gd — CanvasLayer (layer 17) bottom-sheet
  grid: rows=pawns × cols=8 work categories. Each cell tap-cycles
  1→2→3→4→0→1, color-coded (red/orange/yellow/blue/gray). Writes back
  to pawn.work_priorities + emits pawn_priority_changed.
- scenes/ui/alerts_log.gd — CanvasLayer (layer 19) ring buffer 50
  entries. Newest first, severity icon (info/warn/danger), Day HH:MM
  timestamp, Go-there camera pan. Listens to alert_added +
  storyteller_event_fired + day_ended.
- EventBus.request_wolf_spawn wired end-to-end: EventCatalog
  _spawn_wolves emits; WolfSpawner._on_request_wolf_spawn force-spawns
  bypassing the darkness/cooldown gates.
- Clock emits EventBus.day_ended(summary) at dusk→night transition.

Top bar buttons added in order: ‖ / 1× / 5× / 12× / Save / Load /
Settings / Build / Work / Log[N]. Plus the ⊕ FAB at bottom-right.

MCP runtime verified all 4 surfaces via screenshot:
- PawnDetailPanel: Bram shows Crafting=8 / Cooking=2 / Manual=0
  matching seed; bars green; Mood: 50; work-priorities readout
- BuildDrawer: 4 tabs visible, Designate tab shows Chop/Mine/Dig grave/
  No roof buttons with procedural icons
- WorkPriorityMatrix: 3 pawns × 8 categories, all '3' (NORMAL default)
  cells in yellow, tap-to-cycle ready
- AlertsLog: 4 entries — red 'Wolf pack approaching!' danger, blue
  'Bram is at the cabin' info, yellow 'Test alert' warn, blue 'Spring
  Awakens' from boot storyteller roll. Go-there button per entry.

Mouse drag-paint works as-is (user noted). Existing
Selection/Designation _unhandled_input handles drag.

Deferred to Phase 17.5 polish:
- Per-pawn/per-job view layers on the matrix
- Stockpile 4×4 chip filter UI (paint creates 1×1 zones today)
- Bill UI for workbenches (programmatic only today)
- 'No stockpile accepts X' / 'Bill blocked' alert emit wiring
- DaySummaryCard visual (signal emits today, no card UI)
- Wanderer recruit UI, resource buff system

Delegation: 3× gdscript-refactor (Sonnet) agents in parallel;
integration + MCP verify on Opus.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 19:45:35 +01:00

206 lines
10 KiB
GDScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

extends Node
## i18n string table — player-visible strings ONLY. Code keys, EN values.
##
## Locked from day one (per CLAUDE.md): no hardcoded display copy in scenes or
## scripts. If you have player-facing text, add a key here and call Strings.t(key).
##
## Locale switching is post-MVP; the indirection lands now so we don't have to
## retrofit the whole game later. When the table grows, move it to a .tres or
## external CSV import; the public API (`Strings.t(key)`) stays the same.
const TABLE: Dictionary = {
# Phase 0 placeholder — populate as features land.
&"app.title": "Rimlike",
&"smoke.hello": "Phase 0 — autoloads online.",
# Speed controls (top bar)
&"speed.pause": "",
&"speed.normal": "1×",
&"speed.fast": "5×",
&"speed.ultra": "12×",
# HUD
&"hud.tick": "Tick: {n}",
# Phase 11 — in-game clock display ("{d}" = day, "{t}" = "HH:MM")
&"clock.format": "Day {d}, {t}",
# Phase 12 — season indicator ("{s}" = season name, "{d}" = 1-indexed day, "{total}" = days per season)
&"season.spring": "Spring",
&"season.summer": "Summer",
&"season.autumn": "Autumn",
&"season.winter": "Winter",
&"season.format": "{s} {d}/12",
# Pawn state labels
&"pawn.state.idle": "idle",
&"pawn.state.walking": "walking",
# Item types (player-visible this phase)
&"item.wood": "Wood",
&"item.stone": "Stone",
&"item.iron_ore": "Iron ore",
# Item stack count badge ("{n}" is substituted at call site via .format())
&"item.stack_count": "×{n}",
# Phase 6 — new item types (carpenter bench + smelter outputs)
&"item.plank": "Plank",
&"item.stone_block": "Stone block",
# Phase 7 — food loop and cooking chain item types
&"item.flour": "Flour",
&"item.bread": "Bread",
&"item.meal": "Meal",
# Phase 7 — cooking workbench labels
&"workbench.hearth": "Hearth",
&"workbench.millstone": "Millstone",
# Phase 7 — pawn hunger states
&"pawn.state.eating": "eating",
&"pawn.state.hungry": "hungry",
# Phase 11 — mood thoughts (player-visible in pawn-detail, Phase 17)
&"thought.in_darkness": "In darkness",
# Phase 6 — quality tier labels
&"quality.shoddy": "Shoddy",
&"quality.normal": "Normal",
&"quality.excellent": "Excellent",
&"quality.masterwork": "Masterwork",
&"quality.legendary": "Legendary",
# Phase 15 — Storyteller UI buttons
&"ui.go_there": "Go there",
&"ui.dismiss": "Dismiss",
# Phase 16 — Save/Load UI
&"ui.save": "Save",
&"ui.load": "Load",
&"ui.saved": "Saved",
&"ui.saving": "Saving…",
&"ui.no_saves": "No saves yet.",
&"ui.continue": "Continue",
&"ui.cancel": "Cancel",
&"ui.manual_save": "Manual save",
&"ui.autosave": "Autosave",
&"ui.version_mismatch": "This save is from an older version (v{v}) — loading may fail. Continue?",
&"ui.welcome_back": "Welcome back — away {n}",
&"ui.welcome_back_min": "{n} minute",
&"ui.welcome_back_mins": "{n} minutes",
&"ui.welcome_back_hour": "{n} hour",
&"ui.welcome_back_hours": "{n} hours",
&"ui.load_failed": "Load failed (corrupt or version mismatch).",
# Phase 15 — Storyteller event titles + bodies (25-event corpus).
# EventDef factories in EventCatalog carry the English string directly;
# these keys exist so Strings.t() is the indirection point for future locale
# switching. When a locale ships, swap EventDef.title/body from these keys
# instead of touching EventCatalog factories. (%pawn% is substituted by UI.)
&"event.first_beds.title": "First Beds",
&"event.first_beds.body": "Your settlers slept on the cold ground again. They are starting to ache.",
&"event.empty_larder.title": "Empty Larder",
&"event.empty_larder.body": "The larder is bare. Spring won't last forever.",
&"event.no_fire.title": "No Fire",
&"event.no_fire.body": "Without a hearth, the cold will bite by night.",
&"event.walls.title": "Walls?",
&"event.walls.body": "Sleeping under stars is romantic until the wolves arrive.",
&"event.spring_awakens.title": "Spring Awakens",
&"event.spring_awakens.body": "The thaw runs in every stream. Crops will grow fast now.",
&"event.summers_heat.title": "Summer's Heat",
&"event.summers_heat.body": "The sun beats down. Unsheltered work will tire faster.",
&"event.autumns_harvest.title": "Autumn's Harvest",
&"event.autumns_harvest.body": "The fields are heavy with the last of the year's bounty.",
&"event.winters_edge.title": "Winter's Edge",
&"event.winters_edge.body": "Frost has come. The road is closed; you are alone.",
&"event.a_traveler.title": "A Traveler",
&"event.a_traveler.body": "A weary traveler stumbles toward your gate. They look hungry. Will you welcome them?",
&"event.the_refugee_family.title": "The Refugee Family",
&"event.the_refugee_family.body": "A family fleeing bandits arrives. They have nothing, but they would work hard.",
&"event.the_old_soldier.title": "The Old Soldier",
&"event.the_old_soldier.body": "A retired soldier offers his blade for a place by your fire. Combat 8, but old and tired.",
&"event.the_wandering_healer.title": "The Wandering Healer",
&"event.the_wandering_healer.body": "A traveling healer asks for shelter. She brings knowledge of medicine.",
&"event.wolves_at_the_edge.title": "Wolves at the Edge",
&"event.wolves_at_the_edge.body": "Wolves howl in the distance. They will be here by nightfall.",
&"event.lone_wolf.title": "Lone Wolf",
&"event.lone_wolf.body": "A starving wolf circles your livestock.",
&"event.pack_hunt.title": "Pack Hunt",
&"event.pack_hunt.body": "A hunting pack moves through the forest. They smell your colony.",
&"event.bandit_scouts.title": "Bandit Scouts",
&"event.bandit_scouts.body": "Strange figures watched from the treeline at dusk. Bandits, perhaps.",
&"event.fever.title": "Fever",
&"event.fever.body": "%pawn% woke with a fever. The sickness may spread.",
&"event.a_bad_cut.title": "A Bad Cut",
&"event.a_bad_cut.body": "%pawn% gashed their hand chopping wood. The wound looks deep.",
&"event.the_sleeplessness.title": "The Sleeplessness",
&"event.the_sleeplessness.body": "%pawn% has barely slept. Something weighs on them.",
&"event.bountiful_harvest.title": "Bountiful Harvest",
&"event.bountiful_harvest.body": "Your fields exceeded the season. The granary swells.",
&"event.lumberjacks_luck.title": "Lumberjack's Luck",
&"event.lumberjacks_luck.body": "%pawn% found a copse of unusually thick trees.",
&"event.veins_of_iron.title": "Veins of Iron",
&"event.veins_of_iron.body": "A miner reports a rich vein, deeper than expected.",
&"event.strange_stones.title": "Strange Stones",
&"event.strange_stones.body": "Settlers report finding carved stones in the wood — older than any memory.",
&"event.an_old_map.title": "An Old Map",
&"event.an_old_map.body": "%pawn% found a tattered map. Roads to the north, half-faded.",
&"event.one_year_survived.title": "One Year Survived",
&"event.one_year_survived.body": "A full year. The first frost feels different now — yours is a real settlement.",
# Phase 17 — PawnDetailPanel
&"ui.detail.close": "X",
&"ui.detail.hp": "HP",
&"ui.detail.hunger": "Hunger",
&"ui.detail.sleep": "Sleep",
&"ui.detail.mood": "Mood",
&"ui.detail.job": "Job",
&"ui.detail.idle": "Idle",
&"ui.detail.sulking": "Sulking",
&"ui.detail.thoughts": "Thoughts",
&"ui.detail.statuses": "Statuses",
&"ui.detail.skills": "Skills",
&"ui.detail.priorities": "Work priorities",
&"ui.detail.skill.manual_labor": "Manual",
&"ui.detail.skill.crafting": "Crafting",
&"ui.detail.skill.cooking": "Cooking",
&"ui.detail.skill.medicine": "Medicine",
&"ui.detail.skill.combat": "Combat",
&"ui.detail.sev": "sev={s}/{m}",
# Phase 17 — SettingsMenu
&"ui.settings.title": "Settings",
&"ui.settings.speeds": "Speeds",
&"ui.settings.shortcuts": "Pause=Space 1×=1 5×=2 12×=3",
&"ui.settings.auto_pause": "Auto-pause",
&"ui.settings.pause_threat": "On Threat",
&"ui.settings.pause_wanderer": "On Wanderer",
&"ui.settings.pause_pawn_down": "On Pawn-Down",
&"ui.settings.pause_modal": "On Modal",
&"ui.settings.audio": "Audio",
&"ui.settings.master": "Master",
&"ui.settings.music": "Music",
&"ui.settings.sfx": "SFX",
&"ui.settings.ambient": "Ambient",
&"ui.settings.accessibility": "Accessibility",
&"ui.settings.larger_text": "Larger Text",
&"ui.settings.reduce_motion": "Reduce Motion",
&"ui.settings.save": "Save",
&"ui.settings.cancel": "Cancel",
&"ui.settings.btn": "Settings",
# Phase 17 — BuildDrawer bottom-sheet.
&"ui.build": "Build",
&"ui.build_drawer.designate": "Designate",
&"ui.build_drawer.build": "Build",
&"ui.build_drawer.stockpile": "Stockpile",
&"ui.build_drawer.cancel": "Cancel",
&"tool.chop": "Chop trees",
&"tool.mine": "Mine rocks",
&"tool.dig_grave": "Dig grave",
&"tool.no_roof": "No roof",
&"tool.build_wall_stone": "Stone wall",
&"tool.build_wall_wood": "Wood wall",
&"tool.build_floor_wood": "Wood floor",
&"tool.build_floor_stone": "Stone floor",
&"tool.build_door": "Door",
&"tool.build_crate": "Crate",
&"tool.build_bed": "Bed",
&"tool.build_torch": "Torch",
&"tool.workbench_carpenter": "Carpenter",
&"tool.workbench_smelter": "Smelter",
&"tool.workbench_millstone": "Millstone",
&"tool.workbench_hearth": "Hearth",
&"tool.workbench_cremation_pyre": "Cremation Pyre",
&"tool.stockpile_general": "Stockpile",
&"tool.graveyard": "Graveyard",
}
func t(key: StringName) -> String:
if TABLE.has(key):
return TABLE[key]
push_warning("Strings.t(): missing key %s" % key)
return String(key)