# Fire, water, ice and electricity (world.elements) Readable offline: `gripforge docs world-elements`, or the MCP tool `gripforge_docs` (topic `world-elements`). ## What it is for `world.elements` simulates fire, water, ice, electricity, poison and temperature. Things are made of materials (wood, grass, metal, water, ice, cloth...) and take states (burning, wet, frozen, electrified, poisoned, hot, cold) from interaction rules: fire spreads through wood and grass, rain and water put it out, cold freezes water, heat melts ice, lightning electrifies metal and water, poison spreads on contact. The result is deterministic: no randomness, the same scene burns the same way everywhere. The kit decides the states; other kits reach them by contract (damage per second through `combat.core`, walk speed through the character motor, grip, particles). Materials, rules and climates are project data, so a designer or an AI agent extends it by writing documents, without code. Each element can be switched off. ## Turn it on ```text gripforge_gamekit_install { project_id: "gkp_…", id: "world.elements" } gripforge_gamekit_configure { project_id: "gkp_…", id: "world.elements", config: { "temperature": 18, "tagMaterials": { "crate": "wood" }, "damage": { "burning": 4 } } } ``` The kit requires `game.engine`. An archetype makes its instances subjects with the component `material`: `{ "material": { "material": "wood" } }` (also `states`, `radius`, `fixed`). ## First example A scene holds a wooden crate created with `{ "elements": { "material": "wood", "states": ["burning"], "radius": 0.6 } }`, a second crate 1.6 metres away, a cloth rag, a barrel of oil, a pond, a block of ice, an electrified iron pole with a chain beside it, and a vat of poison. Stepping the simulation emits `elements.state` events as the rules play: the burning crate and its flammable neighbours become `burning` and `hot`, subjects next to the pond become `wet`, the charge of the pole spreads to the chain, and later the block of ice melts into water (`elements.material` with `from` `ice` and `to` `water`). Subjects are entities with an `elements` component, tagged entities mapped in `tagMaterials`, the player, and anything registered with `register()`. ## Settings and defaults | Setting | Default | Meaning | |---|---|---| | `fire`, `water`, `ice`, `electricity`, `poison` | `true` | switch an element (its rules and states) off | | `climate` | `true` | simulate the ambient temperature and the hot and cold states | | `temperature` | `18` | base ambient temperature in degrees C | | `altitudeCooling`, `altitudeRef` | `6`, `0` | degrees lost per 100 m above `altitudeRef` | | `weatherTemperature` | `{}` | degrees added per `world.weather` preset (default: snow -12, blizzard -22, rain -4) | | `fireWarmth`, `fireWarmthRadius` | `25`, `6` | degrees a fire adds at its centre, fading to 0 at the radius in metres | | `hotAbove`, `coldBelow` | `40`, `2` | thresholds of the `hot` and `cold` states | | `tickRate` | `10` | element steps per second | | `groundCells` | `true` | fire spreads cell by cell over flammable ground and plants of `world.terrain` | | `cellSize`, `maxCells` | `2`, `1024` | ground cell size in metres; ceiling of live cells | | `groundMaterials` | `{}` | terrain layer to material (default: grass and moss burn as grass) | | `playerMaterial` | `flesh` | material of the player; empty: the player is not a subject | | `tagMaterials` | `{}` | entity tag to material, for example `{ "crate": "wood" }` | | `damage` | `{}` | damage per second per state (default burning 4, electrified 6, poisoned 1.5, cold 0.5, hot 0.5) | | `speed` | `{}` | walk speed factor per state (default frozen 0, electrified 0.4, cold 0.85, burning 1.15, poisoned 0.9) | | `wetGrip`, `frozenGrip` | `0.55`, `0.4` | grip of a wet or frozen subject | | `lightning`, `lightningRadius` | `true`, `40` | the lightning of `world.weather` strikes the highest metal subject within the radius | | `builtinRules` | `true` | start from the built-in rules | | `disabledRules` | `[]` | ids of built-in or project rules to switch off | | `materials`, `rules` | `[]` | extra or overridden materials and rules | | `despawnConsumed` | `false` | destroy entities whose material burns away | ## States, materials and rules Each subject has heat (degrees C), water, charge, poison (0 to 1) and fuel (seconds of burning). States are thresholds: burning (flammable, fuel left, heat at or above ignition, not wet), wet (water at or above 0.3), frozen, electrified (charge at or above 0.2), poisoned (poison at or above 0.2), hot and cold. A material can also change: water freezes into ice, ice and snow melt into water, wood burns into ash. Built-in materials: wood, grass, cloth, oil, flesh, metal, stone, sand, ash, water, salt_water, ice, snow, poison, lava. A material is `{ id, flammable, ignition, fuel, burnsInto, conductive, metal, floats, liquid, toxic, solidIce, freezesInto, freezeAt, meltsInto, meltAt, inertia }`. A rule makes subjects matching `from` add quantities per second (`add`) to those matching `to` within `range` metres, scaled by distance when `falloff` is set. It belongs to a `group` (fire, water, ice, electricity, poison, temperature) and matches on `state`, `notState`, `material`, `prop`, `tag`, and for a source `weather` (rain, snow) or `submerged`. ```json { "id": "fire_spreads", "group": "fire", "from": { "state": "burning" }, "range": 2, "add": { "heat": 260 }, "falloff": true } ``` Built-in rule ids, usable in `disabledRules`: fire_spreads, fire_dries, fire_feeds_itself, rain_wets, snow_chills, water_soaks, water_wets_contact, water_douses, cold_spreads, electricity_conducts, electricity_through_water, electricity_fades, poison_on_contact, poison_fades, water_evaporates, heat_dries. ## Services, events, variables - `world.elements` (service): `register`, `states`, `has`, `modifiers`, `temperatureAt`, `apply`, `ignite`, `douse`, `electrify`, `freeze` (a target is an entity or a position, the ground cell there), `snapshot`, `rules`, `addRule`, `removeRule`, `materials` and `defineMaterial`. `modifiers(entity)` returns the speed and grip factors for AI and vehicle kits. - `elements.state` (event): `{ entity, state, on }`, a subject entered or left a state. - `elements.material` (event): `{ entity, from, to }`, for example water froze into ice. - `elements.burnt` (event): `{ entity, into, at, radius }`, burnt out; `into` is null when the entity is consumed. - `elements.cell` (event): `{ entity, material, at }`, a ground cell joined the simulation next to a fire. - `elements.lightning` (event): `{ entity, at }`, a subject was struck. - `world.temperature`, `player.temperature` and `player.elements` (variables): ambient temperature at the player, body temperature and the player's states. - Collections `element_materials`, `element_rules` and `element_climates`. A climate is `{ zone, temperature, set }`: degrees added inside a project zone, or the temperature itself with `set`. A scene may carry its own `element_climates`. The ambient temperature is `temperature` minus the altitude cooling, plus the weather preset, plus climate zones, plus nearby fires. The kit is saved with the game, including subjects, run-time rules and materials. ## Hooks and modding - `elements.enter` `{ entity, state, material }`: asked once when an entity (never a ground cell) is about to take a state. Cancelled, it does not take the state for as long as the engine keeps giving it (a fireproof boss). - `elements.strike` `{ entity, heat }`: asked before a lightning strikes a subject. A tap may change `heat` (default added: 400); cancelled, no strike. ```json { "id": "fireproof", "hook": "elements.enter", "match": { "entity": "e7", "state": "burning" }, "cancel": true } ``` A mod may override the settings (all but `tickRate`, `cellSize`, `maxCells`, `materials` and `rules`) and add, patch or remove documents of `element_materials`, `element_rules` and `element_climates`. ## Engines The same rule engine (same rules, same order, same thresholds) runs on the web player, the native player and the Godot, Unity and Unreal wrappers, which draw the states with native particles (flames, smoke, frost, sparks, poison) and expose events as signals or events of the engine. The hooks run on the web and Rust hosts, and through the Rust kit logic in the engines that load it. ## When it does not do what you expect - Nothing burns: the subject is not registered (add `material` to its archetype, a `tagMaterials` entry or call `register`), or its material is not flammable, or `fire` is `false`. - A fire goes out at once: the subject is wet, or a rule such as water_douses applies. - The ground does not burn: `groundCells` is `false`, `world.terrain` is absent, or the layer is not in `groundMaterials`. - No damage from a state: the entity has no health, or `damage` sets that state to 0. - An `elements.enter` tap keeps firing: the engine keeps giving the state; the tap holds it back for as long as that lasts. ## Limits Ground cells never run a hook. Burning out (`elements.burnt`) is not interceptable. The simulation is a set of rules on quantities, not a fluid or a physics solver. ## Versions Kit 1.3.0. 1.1.0 added the engine content (the `material` component, scene climates), 1.2.0 the hooks and moddable collections, 1.3.0 declared `into` of `elements.burnt` as nullable.