diff --git a/content/global/krenn-industrial-zone.ron b/content/global/krenn-industrial-zone.ron index 11918f376..c0945a2e4 100644 --- a/content/global/krenn-industrial-zone.ron +++ b/content/global/krenn-industrial-zone.ron @@ -1,19 +1,21 @@ -// Krenn Industrial Zone — location-specific zone content +// Krenn Industrial Zone — location metadata // // Schema: server/src/npc/blueprint.rs :: ZoneSpec -// Ticket: #609, #630 (copy team) +// Ticket: #609, #630, #661 (copy team) // Validate: tooling/validate-ron content/global/krenn-industrial-zone.ron zone // -// This is content for a specific location: a Krenn industrial district. -// Behaviors, roles, and social sites are culture×zone specific — not reusable -// templates. See Q-057 for the composable behavior generation design that -// will replace hand-authored pools with assembled primitives. +// Location-specific metadata for a Krenn industrial freight district. +// Behavior primitives have moved to the zone-type template: +// content/global/zone-types/industrial_freight.ron +// +// This file holds: zone_type reference, location metadata, role weights, social sites. +// The generator reads zone_type to find the primitive pool; overrides come from here. // // Character: freight handling, manufacturing, maintenance. High throughput. // Shift rhythms. Functional over comfortable. Nobody lingers — unless they're on break. ( - zone_type: "industrial", + zone_type: "industrial_freight", label: "Industrial Zone", description: "Freight handling, manufacturing, and maintenance. High throughput, shift-based work rhythms, functional over comfortable. Faces are known by role and bay number more than name. The work doesn't stop between shifts — people do.", @@ -22,139 +24,13 @@ // 1-10. Dense. Multiple shifts overlap. Crowds at handover. population_density: 6, - roles: [ - ( - id: "dock_worker", - label: "Dock Worker", - // Most common. The zone runs on their backs. - weight: 5, - skill_focus: ["technical"], - combat_eligible: false, - typical_behaviors: [ - "guides a freight container into position with hand signals", - "checks a manifest against a handheld scanner, lips moving", - "waits at the loading bay apron with arms crossed, watching the clock", - "calls bay numbers to a colleague across the noise of the floor", - "hooks a cargo sling and steps clear before signaling the lift", - "stacks empty pallets against a wall with mechanical efficiency", - "wipes sweat from her face with a forearm and keeps moving", - "slumps into a break room chair and stares at nothing for a full minute before reaching for a drink", - // on-shift - "drags a heavy case along the deck plating one-handed, leaning hard into the weight", - "re-checks a seal on a container door after a colleague already checked it", - "flags a damaged pallet to the foreman without stopping the line", - "shoulders a cargo rig harness and clips in without looking down", - "sweeps debris off the loading apron with a long push broom", - "braces a container with a boot while reaching for the locking pin", - "reads the load ticket twice, then flips the handheld over to check the back", - "waves off a crane operator when the angle is wrong, holds up a fist", - "steps over a bundled cable run without breaking stride", - "peels off a work glove with his teeth to check a handheld display", - "trades a quick look with a colleague when the foreman walks by", - // off-shift / break room - "unwraps a meal packet in the break room and eats standing at the counter", - "passes a drink to the person next to her without being asked", - "leans back in a break room chair with eyes closed, boots crossed at the ankle", - "laughs at something across the break room table, loud enough to carry", - "shows something on a handheld to a colleague and both of them look at it for a moment", - "sits with elbows on knees, turning an empty cup in both hands", - "splashes water on his face at the sink and stands there a moment before turning off the tap", - "talks over the break room noise at volume, gesturing with a fork", - "falls asleep in a break room chair, chin on chest, arms folded", - ], - ), - ( - id: "technician", - label: "Systems Technician", - // Keeps the infrastructure running. Never enough of them. - weight: 4, - skill_focus: ["technical"], - combat_eligible: false, - typical_behaviors: [ - "runs a diagnostic routine on a floor console, eyes on the readout", - "traces a conduit run along the ceiling with a handheld light", - "swaps a panel module with practiced speed and no wasted motion", - "logs a fault code into a datapad before moving on", - "presses an ear to a vibrating duct and listens", - "argues quietly with a display that isn't giving the right numbers", - "queries a fault log through her insert without touching the terminal, eyes briefly unfocused", - "stretches both arms overhead in the break room doorway, blocking it without noticing", - // on-shift - "taps a wrench against a junction box lid to test for rattle", - "pulls a burnt relay from a panel and holds it up to the light", - "clips a sensor lead to two terminals and watches the readout settle", - "photographs a fault site with a handheld before touching anything", - "threads a cable through a conduit run without looking, hands working by feel", - "checks a pressure gauge by putting a thumb on the dial housing and reading the needle", - "labels a repaired junction with tape and a marker, block letters", - "reads a service manual on a battered datapad, scrolling with one finger", - "kneels under a raised floor panel with a light between her teeth", - "closes a maintenance hatch and shoulder-checks it twice", - "stands on the second rung of a ladder and reaches without climbing higher", - // off-shift / break room - "sits sideways in a break room chair, back against the wall, feet on the seat beside her", - "pulls up a schematic on a personal handheld and looks at it between bites", - "refills someone else's cup from the urn without commenting on it", - "puts her boots on the break room table and doesn't move them when the foreman walks in", - "describes a problem to a dock worker who doesn't follow it but nods anyway", - "argues a point at the break room table, tapping the surface for emphasis", - "reads something on a personal device with his head tipped back and the screen held at arm's length", - "laughs until he has to set down his drink", - ], - ), - ( - id: "foreman", - label: "Shift Foreman", - // Fewer of them. High visibility. Everyone knows where they are. - weight: 2, - skill_focus: ["observation", "persuasion"], - combat_eligible: false, - typical_behaviors: [ - "walks the floor with a datapad under one arm and says nothing", - "pulls a worker aside for a quiet word near the far wall", - "marks a line off a production board and moves to the next one", - "stands at the mezzanine rail watching throughput without expression", - "reviews shift handover notes and circles something with a stylus", - "speaks to a dock crew in a low voice — they listen without nodding", - "sits alone in the break room rubbing the back of her neck, datapad face-down on the table", - "laughs at something a technician says, then catches herself and goes quiet", - // the person beneath the role - "covers a worker's absence from the shift log by redistributing the bay assignments", - "eats lunch standing at a wall terminal so she can watch the floor at the same time", - "takes the call herself instead of forwarding it, one hand pressed to her other ear against the noise", - "corrects a dock worker's form on the cargo rig harness without making it a lesson", - "walks a new hire through the handover checklist once, point by point, no shortcuts", - "keeps a junior worker between herself and the inspection team as the inspectors pass through", - "finds a reason to be nearby when a new worker makes her first solo lift", - "absorbs a production shortfall report without passing the frustration down the line", - "hands a dock worker an extra meal packet and walks away without explaining it", - "sits next to a technician in the break room and doesn't talk, just sits", - "makes a note in the shift log that takes longer to write than it takes to read", - "tells a bad joke to nobody in particular while marking off the production board", - "signs off on a repair she didn't inspect, because she knows who did it", - "stands at the edge of the loading floor for a long moment before walking back", - ], - ), - ( - id: "security", - label: "Facility Security", - // Present, watchful. Not looking for trouble — cataloguing it. - weight: 2, - skill_focus: ["combat", "observation"], - combat_eligible: true, - typical_behaviors: [ - "sweeps the access corridor on a timed circuit, same path each time", - "waves a regular through the checkpoint on sight — scans the one behind them out of procedure", - "leans at the restricted bay entrance, arms folded — been watching this corridor since the shift started", - "notes something in a shift log without reacting to it outwardly", - "watches a handover between crews from across the loading floor", - "stops at a junction, looks both ways, and picks the longer route", - "runs an ID check on someone whose face she recognizes, procedure is procedure", - "stands with her back to a structural column where both exits are visible", - "glances at a badge without stopping the person wearing it", - "checks the restricted bay door seal before settling in to watch the corridor", - ], - ), + // Role presence and weights for this location. + // skill_focus / combat_eligible / behavior_primitives live in the zone-type template. + role_weights: [ + ( id: "dock_worker", weight: 5 ), + ( id: "technician", weight: 4 ), + ( id: "foreman", weight: 2 ), + ( id: "security", weight: 2 ), ], social_sites: [ @@ -162,7 +38,6 @@ site_type: "break_room", label: "Worker Break Room", // Between shifts. Decompression. People stop performing for a moment. - roles: ["dock_worker", "technician", "foreman"], min_npcs: 2, max_npcs: 5, ), @@ -170,7 +45,6 @@ site_type: "maintenance_bay", label: "Maintenance Bay", // Active work site. Technicians and dock workers cross paths here. - roles: ["technician", "dock_worker"], min_npcs: 2, max_npcs: 4, ), @@ -178,9 +52,11 @@ site_type: "loading_platform", label: "Loading Platform", // The operational center. Busy, loud, coordinated. - roles: ["dock_worker", "foreman", "security"], min_npcs: 3, max_npcs: 8, ), ], + + abandoned: false, + poi_overlay: None, ) diff --git a/content/global/krenn-rural-zone.ron b/content/global/krenn-rural-zone.ron index d3f2ebf7c..0c727deac 100644 --- a/content/global/krenn-rural-zone.ron +++ b/content/global/krenn-rural-zone.ron @@ -1,19 +1,21 @@ -// Krenn Rural Zone — location-specific zone content +// Krenn Rural Zone — location metadata // // Schema: server/src/npc/blueprint.rs :: ZoneSpec -// Ticket: #609, #630 (copy team) +// Ticket: #609, #630, #661 (copy team) // Validate: tooling/validate-ron content/global/krenn-rural-zone.ron zone // -// This is content for a specific location: a Krenn rural settlement. -// Behaviors, roles, and social sites are culture×zone specific — not reusable -// templates. See Q-057 for the composable behavior generation design that -// will replace hand-authored pools with assembled primitives. +// Location-specific metadata for a Krenn rural agricultural settlement. +// Behavior primitives have moved to the zone-type template: +// content/global/zone-types/rural_agricultural.ron +// +// This file holds: zone_type reference, location metadata, role weights, social sites. +// The generator reads zone_type to find the primitive pool; overrides come from here. // // Character: scattered homesteads and small workshops. Unhurried. Community-bound. // Low throughput, high familiarity. Everyone knows who belongs here. ( - zone_type: "rural", + zone_type: "rural_agricultural", label: "Rural Settlement", description: "Scattered homesteads, small workshops, and communal gathering points. Low population density, strong community bonds, subsistence-plus economy. Work is seasonal and visible — everyone knows what everyone else is doing.", @@ -22,149 +24,21 @@ // 1-10. Sparse. Faces are familiar. Strangers stand out. population_density: 2, - roles: [ - ( - id: "farmer", - label: "Farmer", - // Most common. The settlement runs on food production. - weight: 5, - skill_focus: ["technical"], - combat_eligible: false, - typical_behaviors: [ - "tends rows of low-growing crops with a long-handled hoe", - "lifts a crate of produce onto a flatbed with practiced ease", - "checks the section's light cycle timer before deciding whether to water", - "patches a cracked irrigation pipe with strips of bonding tape", - "calls across a field to a neighbor without looking up from work", - "hauls produce to the market stall before the morning exchange opens", - "checks seedling trays in a low prefab greenhouse", - "runs a thumb along the edge of a cracked irrigation seal, then sets it aside", - "stacks empty crates at the end of a row and knocks dirt off her boots", - "drags a length of hose to a dry section and clamps the fitting by hand", - "kneels at the base of a struggling plant and parts the soil with two fingers", - "leans on a fence post and watches the sky before going back to the row", - "refills a handheld sprayer from a standing drum without spilling", - "ties a row marker to a stake with a short length of wire", - "wipes sweat from her forehead with the back of a gloved hand", - "loads a wheelbarrow and tips it into a compost bin at the field edge", - "pulls a dead plant by the roots and carries it to the burn pile", - "tests soil moisture by pressing a thumb into the ground beside a seedling", - "walks the perimeter of a field and checks the wire for breaks", - "sets two crates down on the market floor and counts the lids twice", - // tavern / off-duty - "nurses a drink at the end of the bar with both hands wrapped around the glass", - "trades short words with the mechanic at the next seat without turning fully around", - "sits with boots off under the table, socked feet flat on the floor", - "refills a neighbor's cup from her own jug without being asked", - "plays a slow tile game with two others at the corner table", - "slides a credit chit across the bar and waits for change without counting it", - "leans back in the chair and stares at the ceiling for a long moment", - ], - ), - ( - id: "mechanic", - label: "Settlement Mechanic", - // One or two per settlement. Everyone knows who to call. - weight: 3, - skill_focus: ["technical"], - combat_eligible: false, - typical_behaviors: [ - "pulls a drive unit from a tiller and examines the worn housing", - "wipes grease on the thigh of her coveralls between jobs", - "explains a repair in clipped shorthand without looking up", - "lines up salvaged parts on a workbench and assesses them", - "welds a seam on a cracked water tank with slow, careful strokes", - "borrows a tool from a neighbor and returns it without being asked", - "taps a seized bolt with a mallet twice before reaching for a longer bar", - "threads a wire through a conduit clip and bites the insulation back with her teeth", - "sets a part down, picks up the spec card beside it, and reads it once", - "uses a straight edge to check the flatness of a repaired flange", - "drains a coolant line into a catch tray and marks the container", - "torques a fastener by feel and then confirms it with a wrench click", - "stacks finished repairs in a corner and photographs them with a handheld", - "jots a note on a strip of tape and sticks it to a part's casing", - "squeezes into a narrow access panel and works by touch", - "straightens up and rolls her neck once before kneeling back down", - // tavern / off-duty - "rinses her hands twice at the basin before sitting down at the bar", - "drops her toolkit bag under the stool and orders without looking at the board", - "listens to a farmer's complaint about a tiller and nods once or twice", - "draws a rough diagram on a napkin to explain something, then folds it away", - "buys a round for the table and returns to her seat before anyone can thank her", - ], - ), - ( - id: "trader", - label: "Itinerant Trader", - // Passes through. Outsider-familiar — not local, not stranger. - weight: 2, - skill_focus: ["persuasion", "observation"], - combat_eligible: false, - typical_behaviors: [ - "squares goods on a fold-out portable display with deliberate care", - "leans back on a stool and watches the foot traffic", - "flicks credit chits across the counter with one thumb, barely glancing down", - "holds eye contact through a long pause, waiting for the price to land", - "watches a regular browse the same shelf as last time and says nothing", - "packs unsold goods with no visible frustration", - "unrolls a cloth display on the counter and weights the corners with small stones", - "lifts a sample item and sets it in the light where a browser can see it clearly", - "rewraps an unsold item and tucks it back in the case with a specific order", - "counts coins into a small tray and slides it across the counter", - "pulls a ledger from the bag, checks one line, and closes it", - "marks a price down on the board with a grease stylus and steps back", - "holds a cracked tool up to show the seller where it failed before handing it back", - "folds the portable display flat and straps it to the pack in two moves", - "lays two items side by side on the counter for a customer to compare", - "wipes down the counter surface with a cloth before setting out the next goods", - ], - ), - ( - id: "militia", - label: "Settlement Militia", - // Rare. Part-time. Knows everyone, trusted because of it. - weight: 1, - skill_focus: ["combat", "observation"], - combat_eligible: true, - typical_behaviors: [ - "walks the fence line at a measured, unhurried pace", - "leans on the gate post with rifle slung, watching the road", - "waves a familiar face through without checking credentials", - "sits in the shade of the gatehouse with a local newsline", - "stops to talk with a passing farmer, eyes still scanning the perimeter", - "checks the charge on a handheld scanner and clips it back to the belt", - "props a boot on the lower fence rail and scans the far end of the road", - "nods to a passing trader and tracks the cart until it clears the gate", - "marks a log entry on a handheld at the end of a perimeter pass", - "steps out of the gatehouse at the sound of an approaching engine", - ], - ), + // Role presence and weights for this location. + // skill_focus / combat_eligible / behavior_primitives live in the zone-type template. + role_weights: [ + ( id: "farmer", weight: 5 ), + ( id: "mechanic", weight: 3 ), + ( id: "trader", weight: 2 ), + ( id: "militia", weight: 1 ), ], social_sites: [ - ( - site_type: "tavern", - label: "Local Tavern", - // The Last Shift equivalent for rural Krenn: functional, familiar, slow. - roles: ["farmer", "mechanic", "trader", "militia"], - min_npcs: 3, - max_npcs: 6, - ), - ( - site_type: "workshop", - label: "Community Workshop", - // Shared space. People fix things together. - roles: ["mechanic", "farmer"], - min_npcs: 2, - max_npcs: 4, - ), - ( - site_type: "market_stall", - label: "Settlement Market", - // Weekly or daily trading post. Commerce and gossip combined. - roles: ["trader", "farmer"], - min_npcs: 1, - max_npcs: 3, - ), + ( site_type: "tavern", label: "Local Tavern", min_npcs: 3, max_npcs: 6 ), + ( site_type: "workshop", label: "Community Workshop", min_npcs: 2, max_npcs: 4 ), + ( site_type: "market_stall", label: "Settlement Market", min_npcs: 1, max_npcs: 3 ), ], + + abandoned: false, + poi_overlay: None, ) diff --git a/content/global/zone-types/industrial_freight.ron b/content/global/zone-types/industrial_freight.ron new file mode 100644 index 000000000..13d1f1539 --- /dev/null +++ b/content/global/zone-types/industrial_freight.ron @@ -0,0 +1,168 @@ +// Industrial Freight Zone-Type Template +// +// Schema: server/src/npc/blueprint.rs :: ZoneTypeTemplate +// Ticket: #661 (copy team) +// Validate: tooling/validate-ron content/global/zone-types/industrial_freight.ron zone_type +// +// Sources: D-141 (zone-type template architecture). +// +// Zone character: freight handling, cargo throughput, shift-based manufacturing. +// High throughput, functional over comfortable. Faces known by role and bay number. +// The work doesn't stop between shifts — people do. +// +// Primitives are CULTURE-NEUTRAL. Culture modifiers (culture-*.ron files) append +// cultural flavor at assembly time. Do not encode cultural attitudes in action text. +// +// Roles: dock_worker, technician, foreman, security +// Social site types: break_room, maintenance_bay, loading_platform + +( + id: "industrial_freight", + subtype: None, + label: "Industrial Freight Zone", + description: "Freight handling, cargo throughput, shift-based work rhythms. Functional over comfortable. Faces known by role and bay number. The work doesn't stop between shifts — people do.", + + // Default economic/density profile. Location specs override. + economic_level: 7, + population_density: 6, + + roles: [ + ( + id: "dock_worker", + label: "Dock Worker", + skill_focus: ["technical"], + combat_eligible: false, + // weight omitted — location specs declare role_weights + behavior_primitives: [ + // OnShift + ( action: "guides a freight container into position with hand signals", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "checks a manifest against a handheld scanner", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "waits at the loading bay apron, watching the clock", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "calls bay numbers to a colleague across the noise of the floor", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "hooks a cargo sling and steps clear before signaling the lift", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "stacks empty pallets against a wall", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "wipes sweat from her face with a forearm and keeps moving", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "drags a heavy case along the deck plating one-handed, leaning into the weight", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "re-checks a seal on a container door after a colleague already checked it", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "flags a damaged pallet to the foreman without stopping the line", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "shoulders a cargo rig harness and clips in without looking down", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "sweeps debris off the loading apron with a long push broom", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "braces a container with a boot while reaching for the locking pin", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "reads the load ticket twice, then flips the handheld over to check the back", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "waves off a crane operator when the angle is wrong, holds up a fist", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "steps over a bundled cable run without breaking stride", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "peels off a work glove with his teeth to check a handheld display", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "exchanges a brief look with a nearby colleague when the supervisor passes", context: OnShift, modifier_hint: Some("authority_response") ), + // OffDuty / break room + ( action: "slumps into a break room chair and stares at nothing for a full minute before reaching for a drink", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "unwraps a meal packet in the break room and eats standing at the counter", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "passes a drink to the person next to her without being asked", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "leans back in a break room chair with eyes closed, boots crossed at the ankle", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "laughs at something across the break room table, loud enough to carry", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "shows something on a handheld to a colleague and both of them look at it", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "sits with elbows on knees, turning an empty cup in both hands", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "splashes water on his face at the sink and stands there a moment before turning off the tap", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "talks over the break room noise at volume, gesturing with a fork", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "falls asleep in a break room chair, chin on chest, arms folded", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ], + ), + ( + id: "technician", + label: "Systems Technician", + skill_focus: ["technical"], + combat_eligible: false, + behavior_primitives: [ + // OnShift + ( action: "runs a diagnostic routine on a floor console, eyes on the readout", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "traces a conduit run along the ceiling with a handheld light", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "swaps a panel module, tools back in the pouch before the cover is latched", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "logs a fault code into a datapad before moving on", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "presses an ear to a vibrating duct and listens", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "argues quietly with a display that isn't giving the right numbers", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "queries a fault log through a terminal, eyes briefly unfocused", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "taps a wrench against a junction box lid to test for rattle", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "pulls a burnt relay from a panel and holds it up to the light", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "clips a sensor lead to two terminals and watches the readout settle", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "photographs a fault site with a handheld before touching anything", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "threads a cable through a conduit run without looking, hands working by feel", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "checks a pressure gauge by putting a thumb on the dial housing and reading the needle", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "labels a repaired junction with tape and a marker, block letters", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "reads a service manual on a battered datapad, scrolling with one finger", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "kneels under a raised floor panel with a light between her teeth", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "closes a maintenance hatch and shoulder-checks it twice", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "stands on the second rung of a ladder and reaches without climbing higher", context: OnShift, modifier_hint: Some("physical_manner") ), + // OffDuty / break room + ( action: "stretches both arms overhead in the break room doorway, blocking it without noticing", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "sits sideways in a break room chair, back against the wall, feet on the seat beside her", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "pulls up a schematic on a personal handheld and looks at it between bites", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "refills someone else's cup from the urn without commenting on it", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "puts her boots on the break room table when off-shift", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "describes a problem to a colleague who doesn't follow it but nods anyway", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "argues a point at the break room table, tapping the surface for emphasis", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "reads something on a personal device with his head tipped back and the screen held at arm's length", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "laughs until he has to set down his drink", context: OffDuty, modifier_hint: Some("social_signal") ), + ], + ), + ( + id: "foreman", + label: "Shift Foreman", + skill_focus: ["observation", "persuasion"], + combat_eligible: false, + behavior_primitives: [ + // OnShift + ( action: "walks the floor with a datapad under one arm and says nothing", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "pulls a worker aside for a quiet word near the far wall", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "marks a line off a production board and moves to the next one", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "stands at the mezzanine rail watching throughput without expression", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "reviews shift handover notes and circles something with a stylus", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "speaks to a crew in a low voice — they listen without nodding", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "covers a worker's absence from the shift log by redistributing the bay assignments", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "eats lunch standing at a wall terminal so she can keep an eye on the work", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "takes the call herself instead of forwarding it", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "corrects a worker's form on a piece of equipment without making it a lesson", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "walks a new hire through the handover checklist once, point by point, no shortcuts", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "keeps a junior worker between herself and the inspection team as the inspectors pass through", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "finds a reason to be nearby when a new worker makes her first solo lift", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "absorbs a production shortfall report without passing the frustration down the line", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "hands a worker an extra meal packet and walks away without explaining it", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "signs off on a repair she didn't inspect, because she knows who did it", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "stands at the edge of the loading floor for a long moment before walking back", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "makes a note in the shift log that takes longer to write than it takes to read", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "tells a bad joke to nobody in particular while marking off the production board", context: OnShift, modifier_hint: Some("social_signal") ), + // OffDuty + ( action: "sits alone in the break room rubbing the back of her neck, datapad face-down on the table", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "laughs at something a colleague says, then catches herself and goes quiet", context: OffDuty, modifier_hint: Some("social_signal") ), + ( action: "sits next to someone in the break room and doesn't talk, just sits", context: OffDuty, modifier_hint: Some("social_signal") ), + ], + ), + ( + id: "security", + label: "Facility Security", + skill_focus: ["combat", "observation"], + combat_eligible: true, + behavior_primitives: [ + // OnShift + ( action: "sweeps the access corridor on a timed circuit, same path each time", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "waves a regular through the checkpoint on sight — scans the one behind them out of procedure", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "leans at the restricted bay entrance, arms folded, watching the corridor", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "notes something in a shift log without reacting to it outwardly", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "watches a handover between crews from across the loading floor", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "stops at a junction, looks both ways, and picks the longer route", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "runs an ID check on someone whose face she recognizes, procedure is procedure", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "stands with her back to a structural column where both exits are visible", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "glances at a badge without stopping the person wearing it", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "checks the restricted bay door seal before settling in to watch the corridor", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "runs the same check routine when the supervisor is watching as when she isn't", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "acknowledges the facility manager's walk-through with a nod and doesn't change her position", context: OnShift, modifier_hint: Some("authority_response") ), + ], + ), + ], + + // Valid social site types for this zone type. + // Location specs declare which appear, with their own label, min_npcs, max_npcs. + social_site_types: [ + ( site_type: "break_room", eligible_roles: ["dock_worker", "technician", "foreman"] ), + ( site_type: "maintenance_bay", eligible_roles: ["technician", "dock_worker"] ), + ( site_type: "loading_platform", eligible_roles: ["dock_worker", "foreman", "security"] ), + ], +) diff --git a/content/global/zone-types/rural_agricultural.ron b/content/global/zone-types/rural_agricultural.ron new file mode 100644 index 000000000..107f2c5ee --- /dev/null +++ b/content/global/zone-types/rural_agricultural.ron @@ -0,0 +1,165 @@ +// Rural Agricultural Zone-Type Template +// +// Schema: server/src/npc/blueprint.rs :: ZoneTypeTemplate +// Ticket: #661 (copy team) +// Validate: tooling/validate-ron content/global/zone-types/rural_agricultural.ron zone_type +// +// Sources: D-141 (zone-type template architecture). +// +// Zone character: scattered homesteads, small workshops, open agricultural land. +// Seasonal work rhythms, low population density, strong community familiarity. +// Work is visible and shared — everyone knows what everyone else is doing. +// +// Primitives are CULTURE-NEUTRAL. Culture modifiers (culture-*.ron files) append +// cultural flavor at assembly time. Do not encode cultural attitudes in action text. +// +// Roles: farmer, mechanic, trader, militia +// Social site types: tavern, workshop, market_stall + +( + id: "rural_agricultural", + subtype: None, + label: "Rural Agricultural Zone", + description: "Crop farming, small workshops, communal settlement. Low density, community-bonded, self-sufficient economy. Work is visible to neighbors — everyone knows what everyone else is doing.", + + // Default economic/density profile. Location specs override. + economic_level: 3, + population_density: 2, + + roles: [ + ( + id: "farmer", + label: "Farmer", + skill_focus: ["technical"], + combat_eligible: false, + // weight omitted — location specs declare role_weights + behavior_primitives: [ + // OnShift + ( action: "works back along a crop row, stopping to pull weeds by the root", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "lifts a crate of produce onto a flatbed and reaches for the next before it settles", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "checks the section's light cycle timer before deciding whether to water", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "patches a cracked irrigation pipe with bonding tape", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "calls across a field to a neighbor without looking up from work", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "hauls produce to the market stall before the morning exchange opens", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "crouches over seedling trays and pinches back a leggy stem that grew sideways", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "runs a thumb along the edge of a cracked irrigation seal, then sets it aside", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "stacks empty crates at the end of a row", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "drags a length of hose to a dry section and clamps the fitting by hand", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "kneels at the base of a struggling plant and parts the soil with two fingers", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "leans on a fence post and watches the sky before going back to the row", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "refills a handheld sprayer from a standing drum", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "ties a row marker to a stake with a short length of wire", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "pulls a glove off to wipe her face, pulls it back on without looking", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "loads a wheelbarrow and tips it into a compost bin at the field edge", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "pulls a dead plant by the roots and carries it to the burn pile", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "tests soil moisture by pressing a thumb into the ground beside a seedling", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "walks the field edge, pulling the wire taut at each span to test the tension", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "sets two crates down on the market floor and counts the lids twice", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "answers an inspector's question without breaking the task rhythm", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "waits for the settlement head to finish speaking before going back to work", context: OnShift, modifier_hint: Some("authority_response") ), + // Social / off-duty + ( action: "nurses a drink at the end of the bar with both hands wrapped around the glass", context: Social, modifier_hint: Some("offduty_posture") ), + ( action: "trades short words with the person at the next seat without turning fully around", context: Social, modifier_hint: Some("social_signal") ), + ( action: "sits with boots off under the table, socked feet flat on the floor", context: Social, modifier_hint: Some("offduty_posture") ), + ( action: "refills a neighbor's cup from her own jug without being asked", context: Social, modifier_hint: Some("social_signal") ), + ( action: "plays a slow tile game with two others at the corner table", context: Social, modifier_hint: Some("offduty_posture") ), + ( action: "slides a credit chit across the bar and waits for change without counting it", context: Social, modifier_hint: Some("offduty_posture") ), + ( action: "leans back in the chair and stares at the ceiling for a long moment", context: Social, modifier_hint: Some("offduty_posture") ), + ], + ), + ( + id: "mechanic", + label: "Settlement Mechanic", + skill_focus: ["technical"], + combat_eligible: false, + behavior_primitives: [ + // OnShift + ( action: "pulls a drive unit from a tiller and examines the worn housing", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "wipes grease on the thigh of her coveralls between jobs", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "explains a repair in clipped shorthand without looking up", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "lines up salvaged parts on a workbench and assesses them", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "welds a seam on a cracked water tank with slow, careful strokes", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "borrows a tool from a neighbor and returns it without being asked", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "taps a seized bolt with a mallet twice before reaching for a longer bar", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "threads a wire through a conduit clip and bites the insulation back with her teeth", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "sets a part down, picks up the spec card beside it, and reads it once", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "uses a straight edge to check the flatness of a repaired flange", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "drains a coolant line into a catch tray and marks the container", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "torques a fastener by feel and then confirms it with a wrench click", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "stacks finished repairs in a corner and photographs them with a handheld", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "jots a note on a strip of tape and sticks it to a part's casing", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "squeezes into a narrow access panel and works by touch", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "straightens up and rolls her neck once before kneeling back down", context: OnShift, modifier_hint: Some("physical_manner") ), + // Social / off-duty + ( action: "rinses her hands twice at the basin before sitting down at the bar", context: Social, modifier_hint: Some("offduty_posture") ), + ( action: "drops her toolkit bag under the stool and orders without looking at the board", context: Social, modifier_hint: Some("offduty_posture") ), + ( action: "listens to a complaint about a piece of equipment and nods once or twice", context: Social, modifier_hint: Some("social_signal") ), + ( action: "draws a rough diagram on a napkin to explain something, then folds it away", context: Social, modifier_hint: Some("social_signal") ), + ( action: "buys a round for the table and returns to her seat before anyone can thank her", context: Social, modifier_hint: Some("social_signal") ), + ], + ), + ( + id: "trader", + label: "Itinerant Trader", + skill_focus: ["persuasion", "observation"], + combat_eligible: false, + behavior_primitives: [ + // OnShift + ( action: "squares goods on a fold-out portable display", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "leans back on a stool and tracks a browser who has checked the same display twice without committing", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "flicks credit chits across the counter with one thumb", context: OnShift, modifier_hint: Some("physical_manner") ), + ( action: "holds eye contact through a long pause, waiting for the price to land", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "watches a regular browse the same shelf as last time and says nothing", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "packs unsold goods without reacting", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "unrolls a cloth display on the counter and weights the corners with small stones", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "lifts a sample item and sets it in the light where a browser can see it clearly", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "rewraps an unsold item and tucks it back in the case with a specific order", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "counts coins into a small tray and slides it across the counter", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "pulls a ledger from the bag, checks one line, and closes it", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "marks a price down on the board with a grease stylus and steps back", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "holds a cracked item up to show where it failed before handing it back", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "folds the portable display flat and straps it to the pack in two moves", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "lays two items side by side on the counter for a customer to compare", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "wipes down the counter surface with a cloth before setting out the next goods", context: OnShift, modifier_hint: Some("work_pace") ), + // Social + ( action: "nurses a drink at the far end of the bar, watching who comes in", context: Social, modifier_hint: Some("environmental_scan") ), + ( action: "talks price with whoever's sitting nearest without making it a pitch", context: Social, modifier_hint: Some("social_signal") ), + ( action: "buys a round and tracks who accepts and who doesn't", context: Social, modifier_hint: Some("social_signal") ), + ( action: "listens more than she talks at the bar, refilling her glass slowly", context: Social, modifier_hint: Some("offduty_posture") ), + ], + ), + ( + id: "militia", + label: "Settlement Militia", + skill_focus: ["combat", "observation"], + combat_eligible: true, + behavior_primitives: [ + // OnShift + ( action: "walks the fence line at a measured, unhurried pace", context: OnShift, modifier_hint: Some("work_pace") ), + ( action: "leans on the gate post with rifle slung, watching the road", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "waves a familiar face through without checking credentials", context: OnShift, modifier_hint: Some("social_signal") ), + // on-duty quiet time — context is OnShift but posture reads as off-duty + ( action: "sits in the shade of the gatehouse reading a local newsline", context: OnShift, modifier_hint: Some("offduty_posture") ), + ( action: "stops to talk with a passerby, eyes still scanning the perimeter", context: OnShift, modifier_hint: Some("social_signal") ), + ( action: "checks the charge on a handheld scanner and clips it back to the belt", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "props a boot on the lower fence rail and scans the far end of the road", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "nods to a passing cart and tracks it until it clears the gate", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "marks a log entry on a handheld at the end of a perimeter pass", context: OnShift, modifier_hint: Some("task_completion") ), + ( action: "steps out of the gatehouse at the sound of an approaching engine", context: OnShift, modifier_hint: Some("environmental_scan") ), + ( action: "reports a situation to the settlement head without editorializing", context: OnShift, modifier_hint: Some("authority_response") ), + ( action: "straightens slightly when the relief officer arrives for handover", context: OnShift, modifier_hint: Some("authority_response") ), + // OffDuty + ( action: "sits at the end of the bar still in kit, drink in hand, not really off yet", context: OffDuty, modifier_hint: Some("offduty_posture") ), + ( action: "catches up with a neighbor over a drink without mentioning work", context: Social, modifier_hint: Some("social_signal") ), + ], + ), + ], + + // Valid social site types for this zone type. + // Location specs declare which appear, with their own label, min_npcs, max_npcs. + social_site_types: [ + ( site_type: "tavern", eligible_roles: ["farmer", "mechanic", "trader", "militia"] ), + ( site_type: "workshop", eligible_roles: ["mechanic", "farmer"] ), + ( site_type: "market_stall", eligible_roles: ["trader", "farmer"] ), + ], +)