docs: add current developer feature index
This commit is contained in:
@@ -0,0 +1,139 @@
|
||||
# Feature slice: authored content and presentation data
|
||||
|
||||
This slice is the no-code extension boundary for content that reuses existing
|
||||
behavior. It is implemented by `SimulationContentPack`, `ContentCatalog`, the
|
||||
typed definition resources under `simulation/definitions/`, and the separate
|
||||
`PresentationCatalog` under `world/presentation/`.
|
||||
|
||||
## The four layers
|
||||
|
||||
| Layer | Lives in | Contains | Never contains |
|
||||
| --- | --- | --- | --- |
|
||||
| Definition | `.tres` resources and typed `Resource` classes | immutable IDs, balance, capabilities, effects, handlers, cue IDs | mutable amount, owner, reservation, node references |
|
||||
| Instance descriptor | placement/provider nodes and regional records | stable runtime ID, context/location, authored overrides | script/callable/`NodePath` authority |
|
||||
| State record | `simulation/state/` | primitive mutable values, IDs, history/event references | scene assets or resource paths |
|
||||
| Presentation binding | `world/presentation/` and scene providers | cue-to-scene/material/icon/animation metadata | simulation quantities or quest authority |
|
||||
|
||||
Definitions are current-build balance. A save stores the definition ID and
|
||||
mutable instance state; it does not freeze the `.tres` path or copy the full
|
||||
resource. Renaming an ID requires an alias/migration, not a silent replacement.
|
||||
|
||||
## Content packs and catalog publication
|
||||
|
||||
`SimulationContentPack` groups typed arrays for:
|
||||
|
||||
- actions, professions, capability tags;
|
||||
- items, resources, storages;
|
||||
- enemies and animals;
|
||||
- situations, dialogue intents, and template catalogs;
|
||||
- event types and social consequences;
|
||||
- required pack IDs and required handler IDs.
|
||||
|
||||
`ContentCatalog.create_core()` loads `simulation/definitions/packs/core.tres`.
|
||||
`ContentCatalog.rebuild()` sorts packs and every definition by stable ID,
|
||||
collects references into temporary dictionaries, validates the complete graph,
|
||||
and publishes only if there are no errors. A failed rebuild clears the
|
||||
published catalog; it never exposes a partially valid pack.
|
||||
|
||||
Validation currently rejects duplicate IDs, unknown references, missing
|
||||
handlers, unsupported situation predicates, missing presentation cues, invalid
|
||||
categories, invalid event/consequence references, duplicate template keys, and
|
||||
malformed typed action contracts. `get_authoring_report()` is the deterministic
|
||||
machine-readable inventory used by tests and tooling.
|
||||
|
||||
The first built-in handler contract is `activity_metric_delta`. It requires an
|
||||
activity target, exactly one positive safety/knowledge metric effect, typed
|
||||
optional `player_multiplier`/`npc_productivity` values, a known completion
|
||||
event, and a routable completion-cost item. This closes the gap where an
|
||||
authored action could publish but produce a fact that the validator could not
|
||||
restore.
|
||||
|
||||
## Adding data-only content
|
||||
|
||||
### New item and route
|
||||
|
||||
1. Add an `ItemDefinition` with a category and stable `item_id`.
|
||||
2. Add a `StorageDefinition` that accepts the item ID or one of its tags, or
|
||||
update an existing typed storage route.
|
||||
3. Add both to a pack and make sure the `StorageRoutingPolicy` can rank a
|
||||
compatible storage.
|
||||
4. Add a `PresentationCueDefinition` only if the item needs a visual.
|
||||
5. Add a conservation/routing test. The herb/apothecary route is the reference
|
||||
example; food/pantry and wood/woodpile preserve legacy coverage.
|
||||
|
||||
### New resource
|
||||
|
||||
1. Add a `ResourceDefinition` with yielded item, gather action, capacity/yield,
|
||||
regrowth, access policy, capability tags, and a cue ID.
|
||||
2. Place a `ResourceNode` with a unique contextual ID and meaningful
|
||||
`safety_risk`, `comfort_distance`, `discovery_priority`, and interaction
|
||||
point.
|
||||
3. Register it through the nearest `ActiveWorldAdapter`; do not add a global
|
||||
array or manager branch.
|
||||
4. Test player/NPC selection, depletion, reservation, unload/rebind, and
|
||||
save/restore authority.
|
||||
|
||||
### New animal
|
||||
|
||||
1. Add an `AnimalDefinition` with behavior/routine/feed capability IDs and a
|
||||
stable presentation cue.
|
||||
2. Add it to `core_animals.tres` or an explicit content pack.
|
||||
3. Spawn through `AnimalFactory` and persist its `animal_definition_id` in
|
||||
`AnimalStateRecord`.
|
||||
4. Reuse `AnimalNode`, `AnimalRoutineSite`, and the grazer visual where the
|
||||
existing contract fits. The goat/sheep pair proves this path.
|
||||
|
||||
### New enemy
|
||||
|
||||
1. Add an `EnemyDefinition` with `behavior_profile_id`, faction, item/weapon
|
||||
references, hostile flag, and cue ID.
|
||||
2. Register it in a pack. `CombatantFactory` owns deterministic per-prefix ID
|
||||
allocation and restore collision checks.
|
||||
3. Spawn through `ConflictSystem.spawn_enemy()`; keep `spawn_wolf()` only as a
|
||||
compatibility wrapper.
|
||||
4. Reuse a behavior profile when possible. `enemy_boar` deliberately reuses
|
||||
`wolf_hunt`; no combat switch was added.
|
||||
|
||||
### New situation or dialogue content
|
||||
|
||||
See [Events through dialogue](FEATURE_EVENTS_KNOWLEDGE_SITUATIONS_DIALOGUE.md).
|
||||
The authored resources must reference existing predicate IDs, event types,
|
||||
intent IDs, template catalogs, and action/item definitions. A definition may
|
||||
describe an unresolved condition, but it cannot create substitute world facts.
|
||||
|
||||
## Presentation catalogs
|
||||
|
||||
`PresentationCatalog` accepts `PresentationCatalogResource` entries whose
|
||||
`PresentationCueDefinition` contains stable cue metadata and optional asset
|
||||
paths. It validates metadata headlessly and loads scenes only at the world
|
||||
boundary. `AnimalDefinition`, enemy definitions, resource definitions, and
|
||||
other simulation content carry only a cue ID. This keeps headless tests and
|
||||
saves independent of imported meshes/materials.
|
||||
|
||||
Presentation catalogs may be absent in a headless `AnimalFactory` or regional
|
||||
simulation. Missing optional presentation is an explicit no-visual result, not
|
||||
a reason to fail simulation state loading.
|
||||
|
||||
## What requires code
|
||||
|
||||
Data-only authoring is guaranteed only when the new combination uses existing
|
||||
typed predicates, capabilities, effects, handlers, behavior profiles, and cue
|
||||
contracts. Add one reusable typed handler when a new mechanic needs a new
|
||||
authority rule. The handler must provide validation, a reason trace, atomic
|
||||
mutation semantics, world facts, save fields/migration if needed, and a real
|
||||
consumer test. Do not solve a new mechanic with a reflection DSL or a script
|
||||
per content asset.
|
||||
|
||||
## Reference tests
|
||||
|
||||
- `tests/content_catalog_test.gd`
|
||||
- `tests/simulation_definitions_test.gd`
|
||||
- `tests/unit/test_authored_situation_dialogue_content.gd`
|
||||
- `tests/unit/test_activity_content_catalog_contract.gd`
|
||||
- `tests/unit/test_content_routing_foundations.gd`
|
||||
- `tests/animal_definition_contract_test.gd`
|
||||
- `tests/unit/test_combatant_factory.gd`
|
||||
- `tests/unit/test_presentation_catalog.gd`
|
||||
|
||||
The [simulation definitions contract](SIMULATION_DEFINITIONS.md) is the
|
||||
authoritative field-level reference; this guide explains the extension path.
|
||||
Reference in New Issue
Block a user