aboutsummaryrefslogtreecommitdiff
path: root/building_guide
diff options
context:
space:
mode:
authorhistoria <[not public]>2026-07-01 03:21:52 -0400
committerhistoria <[not public]>2026-07-01 03:21:52 -0400
commitfbe5090ac3325ff8ea6989cdf4515c7f077c975b (patch)
tree1811ad9c6a596e7177bb2c42944c389c0a120066 /building_guide
parent5f37dc9b6f6b79da04da70ae0c33ec8d02998587 (diff)
downloadthehouseoficarus-fbe5090ac3325ff8ea6989cdf4515c7f077c975b.tar.gz
feat: item messaging standardized, custom messages for production paths implemented
Diffstat (limited to 'building_guide')
-rw-r--r--building_guide/admin.md69
-rw-r--r--building_guide/behaviors.md2
-rw-r--r--building_guide/hazards.md1
-rw-r--r--building_guide/items.md120
-rw-r--r--building_guide/recipes.md24
-rw-r--r--building_guide/rooms.md18
6 files changed, 151 insertions, 83 deletions
diff --git a/building_guide/admin.md b/building_guide/admin.md
index 1c7db93..fbe15d5 100644
--- a/building_guide/admin.md
+++ b/building_guide/admin.md
@@ -40,7 +40,7 @@ etc.) and they receive a notification. Case-insensitive name matching.
```
dig <direction> [name]
```
-Creates a new room in the given direction (north/south/east/west/up/down) from your
+Creates a new room in the given direction (north/south/east/west/ne/nw/se/sw/up/down) from your
current room. The new room ID is auto-generated as the lowest available integer at-or-above
the minimum room ID in the same directory as your current room's YAML file.
@@ -61,7 +61,7 @@ Examples:
undig <direction>
```
Deletes the room in the given direction and removes all exits leading to it from
-every room. Requires confirmation — type `UNDIG <direction>` to proceed, anything
+every room. Requires confirmation — type `y`/`yes` to proceed, anything
else to cancel. The target room's name and ID are shown before deletion. A warning
is displayed if deleting the room would create orphaned (unreachable) rooms.
@@ -196,21 +196,62 @@ Dumps detailed diagnostic information about your current room:
- Connected players in the room
- Live mob instances with HP
+### Web Admin GUI
+
+The server includes a browser-based admin panel for managing all game data visually. It runs alongside
+the game server and is configured in `config.yaml` under `admin_http` (plain HTTP) or `admin_https`
+(TLS with auto-generated self-signed certificate).
+
+#### Setup
+
+1. Ensure your account YAML has `admin: true` (same as in-game admin).
+2. Configure the admin server in `config.yaml`:
+ ```yaml
+ admin_http: ":8080" # listens on port 8080, HTTP
+ # or for HTTPS:
+ admin_https: ":8443"
+ ```
+3. Start the game server. The admin panel is available at `http://<host>:8080` (or `https://<host>:8443`).
+4. Log in with your account name and password (same credentials as in-game).
+
+#### Features
+
+| Page | URL | Description |
+|------|-----|-------------|
+| Map | `/` | Interactive SVG map showing rooms on a 3D grid. Zoom/pan, click rooms to edit, create/delete rooms and exits, relink exits. Up/down links shown alongside horizontal connections. |
+| Items | `/editor/items` | Full CRUD editor with sections for equipment (type/slot/attack/defense/other), tool, craft (type/level/XP/ingredients/stations/tool/steps), firemaking, farming, potions, and requirements. Undo/redo supported. |
+| Objects | `/editor/objects` | CRUD editor with sections for gather (tools/drops/success formula), use (message/wait/consumes), talk (visual talk tree editor), safespot, steal, use_interactions, and on_look. |
+| Mobs | `/editor/mobs` | CRUD for mob definitions — stats, drops, talk, behavior, assassin/steal/task fields. |
+| Drops | `/editor/drops` | CRUD for shared drop tables (gem tables, bird's nests, etc.). |
+| Hazards | `/editor/hazards` | CRUD for hazard definitions. |
+| Techs | `/editor/techs` | CRUD for technology definitions (buffs, drain rates, categories). |
+| Courses | `/editor/courses` | CRUD for agility courses (obstacle sequences, XP, fail damage). |
+| Modules | `/editor/modules` | CRUD for science modules (combat/utility/transport/enchant/processing). |
+| Players | `/editor/players` | Browse character YAML files and view player state. |
+| Flags | `/editor/flags` | View and edit world flags in real time. |
+| Files | `/editor/files` | Raw file tree browser for all YAML files under `data/`. |
+
+All CRUD editors support undo/redo (persisted to `data/.admin_history.json`), so changes can be reverted
+even across sessions.
+
+#### Map Interface
+
+The map page (`/`) is the main navigation hub:
+- Rooms are displayed as colored nodes on a 3D grid, connected by links (bars for two-way, arrows for one-way, X for blocked).
+- Click a room node to edit its properties (name, description, color, exits, objects, mobs, spawns).
+- Drag connections between rooms to create or relink exits.
+- Right-click (or long-press) a room to delete it or access advanced options.
+- The map uses the same BFS-based grid layout as the in-game map, showing all rooms on the current z-plane.
+- Up/down links are shown with special glyphs when connecting rooms on different z-levels.
+
### Workflow
The typical admin worldbuilding workflow:
-1. **Lay out rooms:** Use `dig` to create connected rooms quickly. If `dig` would create a
- grid overlap, a two-way link is created instead — no duplicate rooms. Use `room insert`
- to place a new room between two already-connected rooms without breaking the map grid.
-2. **Flesh out rooms:** Use `room` commands to set names, descriptions, add objects/mobs/spawns
- directly from inside the game. For deeper edits, edit the YAML files directly in
- `data/rooms/` to add on-enter scripts, triggers, hazards, etc.
-3. **Rearrange:** Use `swapid` to renumber rooms and `undig` to delete rooms you no longer want
- (with full exit cleanup). Use `close` to remove individual exits.
+1. **Lay out rooms:** Use `dig` to create connected rooms quickly, or use the web map to create and link rooms visually. If `dig` would create a grid overlap, a two-way link is created instead — no duplicate rooms. Use `room insert` to place a new room between two already-connected rooms without breaking the map grid.
+2. **Flesh out rooms:** Use `room` commands to set names, descriptions, add objects/mobs/spawns directly from inside the game. Use the web admin editors for richer CRUD with undo/redo. For deeper edits, edit the YAML files directly in `data/rooms/` to add on-enter scripts, triggers, hazards, etc.
+3. **Rearrange:** Use `swapid` to renumber rooms and `undig` to delete rooms you no longer want (with full exit cleanup). Use `close` to remove individual exits.
4. **Reload:** Run `reload` to pick up YAML changes without restarting (rooms auto-reload).
5. **Test:** Use `goto` to jump around while debugging room connections and content.
-6. **God mode:** Use `god` to test dangerous areas safely — full stats, no aggro, pass through
- blocked exits. `ungod` restores normal state.
-7. **Debug:** Use `setflag` / `setplayerflag` to test quest logic and conditional content.
- Use `inspect` to check room state, flags, and triggers.
+6. **God mode:** Use `god` to test dangerous areas safely — full stats, no aggro, pass through blocked exits. `ungod` restores normal state.
+7. **Debug:** Use `setflag` / `setplayerflag` to test quest logic and conditional content. Use `inspect` to check room state, flags, and triggers.
diff --git a/building_guide/behaviors.md b/building_guide/behaviors.md
index 0fc6516..3d35036 100644
--- a/building_guide/behaviors.md
+++ b/building_guide/behaviors.md
@@ -510,7 +510,7 @@ Item-specific interaction:
```yaml
name: bookshelf
use_interactions:
- - item: dusty_tome
+ - item_id: dusty_tome
message: "The bookshelf slides aside, revealing a secret passage!"
action:
set_flags:
diff --git a/building_guide/hazards.md b/building_guide/hazards.md
index 26fdccc..5db7ceb 100644
--- a/building_guide/hazards.md
+++ b/building_guide/hazards.md
@@ -33,7 +33,6 @@ required_item: "" # optional: an equipped item that NEGATES the haza
| Field | Description |
|---|---|
-| `id` | Unique identifier (matches the filename) |
| `name` | Display name used in warnings and default messages |
| `description` | Flavour text (for a future `examine`) |
| `attack_type` | `stab`/`slash`/`crush`/`ranged`/`science` — selects which player defense bonus applies and which protection tech reduces the damage (empty = `crush`) |
diff --git a/building_guide/items.md b/building_guide/items.md
index eefdf9c..e03622d 100644
--- a/building_guide/items.md
+++ b/building_guide/items.md
@@ -5,6 +5,10 @@
put an `id:` field in the file — it is ignored. Anything that references this item (drop
tables, craft `ingredients`, room `item_spawns`) uses that filename.
+### Equipment & Tool Blocks
+
+Combat and equipment stats go under an `equipment:` block. Tool stats go under a `tool:` block.
+
```yaml
name: bronze pickaxe
color: "B2" # xterm-256 color index (00-FF)
@@ -12,88 +16,108 @@ aliases: ["pick", "pickaxe"]
description: "A sturdy bronze pickaxe."
value: 10
stackable: false
-equip_slot: main_hand # optional — where it equips
-weapon_type: melee # optional — melee, ranged, or science
-attack_type: stab # stab/slash/crush/ranged/science — determines accuracy type
-stats: # optional — per-type combat bonuses
- stab_attack: 4
- slash_attack: -2
- crush_attack: 2
- strength_bonus: 3
-speed: 5 # ticks between attacks
-tool_type: pickaxe # used by gather behaviors that require "tool: pickaxe"
-tool_speed: 2 # reduces gather wait time
+equipment: # optional — combat/equip behavior
+ type: melee_weapon # melee_weapon / ranged_weapon / tech_weapon / armor / ammo / tool
+ slot: main_hand # head / neck / torso / legs / hands / feet / back /
+ # ammo / main_hand / off_hand / ring
+ attack_type: stab # stab/slash/crush/ranged/science — determines accuracy type
+ speed: 5 # ticks between attacks
+ attack: # accuracy bonuses per type
+ stab: 4
+ slash: -2
+ crush: 2
+ other:
+ strength: 3 # melee max hit bonus
+tool: # optional — tool behavior
+ type: pickaxe # used by gather behaviors that require "tool: pickaxe"
+ speed: 2 # reduces gather wait time
requirements: # optional — skill levels needed to equip
accuracy: 1
```
-### Equipment Stats (ItemStats)
-
-Weapons have per-type **attack bonuses** — these determine accuracy based on the weapon's `attack_type`:
+### Equipment Block Fields
| Field | Description |
|---|---|
-| `stab_attack` | Accuracy bonus for stab attacks |
-| `slash_attack` | Accuracy bonus for slash attacks |
-| `crush_attack` | Accuracy bonus for crush attacks |
-| `science_attack` | Accuracy bonus for science attacks |
-| `ranged_attack` | Accuracy bonus for ranged attacks |
-
-Armor has per-type **defense bonuses** — the mob's `attack_type` determines which defense is used:
-
-| Field | Description |
+| `type` | Equipment type: `melee_weapon` / `ranged_weapon` / `tech_weapon` / `armor` / `ammo` / `tool` |
+| `slot` | Equip slot (see below) |
+| `attack_type` | `stab` / `slash` / `crush` / `ranged` / `science` — determines which defense the target uses |
+| `speed` | Ticks between attacks |
+| `junk` | Junk type this item gives when recycled (for Science decks) |
+| `attack` | Attack bonuses (accuracy) — sub-fields: `stab`, `slash`, `crush`, `ranged`, `science` |
+| `defense` | Defense bonuses — sub-fields: `stab`, `slash`, `crush`, `ranged`, `science` |
+| `other` | Other bonuses — `strength` (melee max hit), `ranged` (ranged max hit on ammo), `science` (science max hit), `technology` (reduces tech battery drain) |
+
+### Equipment Slots
+
+| Slot | Description |
|---|---|
-| `stab_defense` | Defense vs stab attacks |
-| `slash_defense` | Defense vs slash attacks |
-| `crush_defense` | Defense vs crush attacks |
-| `science_defense` | Defense vs science attacks (negative on metal armor) |
-| `ranged_defense` | Defense vs ranged attacks |
-
-Other damage/utility bonuses:
-
-| Field | Description |
-|---|---|
-| `strength_bonus` | Melee max hit bonus |
-| `ranged_strength` | Ranged max hit bonus (on ammo) |
-| `science_damage` | Science max hit bonus |
-| `technology_bonus` | Reduces tech battery drain rate |
+| `head` | Helmets, hats |
+| `neck` | Amulets, necklaces |
+| `torso` | Platebodies, chest armor |
+| `legs` | Platelegs, chaps |
+| `hands` | Gloves, vambraces |
+| `feet` | Boots |
+| `back` | Capes, back items |
+| `ammo` | Arrows, bolts |
+| `main_hand` | Weapons, tools, shields |
+| `off_hand` | Shields, secondary items |
+| `ring` | Rings |
### Attack Type
-Weapons should always set `attack_type`. Common mappings:
+`attack_type` determines which defense stat the target rolls against:
-| Category | attack_type |
+| Weapon | attack_type |
|---|---|
| Swords | slash |
| Daggers | stab |
| Axes | slash |
| Pickaxes | stab |
| Bows | ranged |
+| Science decks | science |
| Unarmed | crush (default) |
-### Equipment Requirements
+### Requirements
Higher-tier equipment requires skill levels to equip:
```yaml
requirements:
accuracy: 20 # melee weapons
- defense: 20 # armor
- ranged: 30 # ranged weapons/armor
+ defense: 20 # armor
+ ranged: 30 # ranged weapons/armor
```
Standard tiers: bronze/iron (none), steel (5), black (10), mithril (20), adamant (30), rune (40), dragon (60).
### Ranged Ammo
-Arrows and bolts use `ranged_strength` for damage. Accuracy comes from the bow:
+Arrows and bolts use `other.ranged` for damage. Accuracy comes from the bow:
```yaml
name: iron arrow
stackable: true
-equip_slot: ammo
-stats:
- ranged_strength: 10
+equipment:
+ other:
+ ranged: 10
+ slot: ammo
+ type: ammo
+```
+
+### Science Decks
+
+Decks use `tech_weapon` type and `science` attack_type:
+
+```yaml
+name: basic deck
+equipment:
+ type: tech_weapon
+ slot: main_hand
+ attack_type: science
+ speed: 5
+ attack:
+ science: 5
```
### Color
@@ -102,8 +126,8 @@ The `color` field accepts xterm-256 palette indices (00-FF, hex) with optional m
```yaml
color: "B2" # bronze/gold
-color: "4B bold" # bold steel blue
-color: "g:C4,D0,E2" # gradient red → orange → gold
+color: "4B bold" # bold steel blue
+color: "g:C4,D0,E2" # gradient red → orange → gold
```
In ANSI mode, extended colors (10-FF) automatically downgrade to the nearest ANSI color. Use `colortable` in-game to see all 256 colors.
diff --git a/building_guide/recipes.md b/building_guide/recipes.md
index e865fa6..96bf0f9 100644
--- a/building_guide/recipes.md
+++ b/building_guide/recipes.md
@@ -18,7 +18,7 @@ Crafting information lives on the **output item's YAML file** via the `craft:` b
| `ingredients` | []IngredientEntry | Ingredients consumed (see below) |
| `output_qty` | int | Quantity produced (default 1, for stackables) |
| `fail` | string | ItemID produced on failure (optional) |
-| `message` | string | Success message per cycle (optional, see message defaults) |
+| `success_message` | string | Success message per cycle (optional, see message defaults) |
| `fail_message` | string | Failure message (optional, empty = silent fail) |
| `start_message`| string | Message when action begins (optional, see message defaults) |
| `end_message` | string | Message when action completes (optional, see message defaults) |
@@ -29,7 +29,7 @@ The output is the item itself — no `output` field needed. The item ID IS the c
### Message Variables
-All message fields (`message`, `fail_message`, `start_message`, `end_message`, and `steps[].message`) support variables that expand to colorized item names:
+All message fields (`success_message`, `fail_message`, `start_message`, `end_message`, and `steps[].message`) support variables that expand to colorized item names:
| Variable | Expands to |
| -------- | ----------------------------------------------- |
@@ -47,7 +47,7 @@ Variables work alongside inline color tags (`{C4}text{/}`) which are expanded af
If a message field is omitted from the YAML, the game uses a skill-level default based on the craft `type`:
-| Type | Default `message` | Default `start_message` |
+| Type | Default `success_message` | Default `start_message` |
|------|-------------------|------------------------|
| `cooking` | `"Cooked to perfection. %n looks great!"` | `"You start cooking %i1."` |
| `smelt` | `"You remove a white hot %n!"` | `"You place the %i1 into the furnace."` |
@@ -81,7 +81,7 @@ craft:
message: "You try to puzzle how the pieces fit together."
- tick: 3
message: "Aha, this edge lines up here!"
- message: "You assemble the map!"
+ success_message: "You assemble the map!"
```
### IngredientEntry — Multi-Item Ingredient Slots
@@ -120,7 +120,7 @@ craft:
quantity: 1
- items: [eye_of_newt]
quantity: 1
- message: "You mix a %n." # %n expands to "stim potion" colored
+ success_message: "You mix a %n." # %n expands to "stim potion" colored
```
### Station-Based Production
@@ -139,8 +139,8 @@ craft:
quantity: 1
- items: [tin_ore]
quantity: 1
- message: "You smelt a %n." # default is "You remove a white hot %n!"
- # overridden here for simpler flavor
+ success_message: "You smelt a %n." # default is "You remove a white hot %n!"
+ # overridden here for simpler flavor
```
```yaml
@@ -154,7 +154,7 @@ craft:
ingredients:
- items: [bronze_bar]
quantity: 1
- # message omitted — uses default "You smith a %n."
+ # success_message omitted — uses default "You smith a %n."
```
For stackable outputs, use `output_qty`:
@@ -171,7 +171,7 @@ craft:
- items: [bronze_bar]
quantity: 1
output_qty: 15
- # message omitted — uses default "You smith a %n."
+ # success_message omitted — uses default "You smith a %n."
```
### Tool-Based Production
@@ -206,7 +206,7 @@ craft:
byproducts: [empty_vial, empty_jug]
- items: [empty_bucket]
quantity: 1
- message: "You pour the %i1 into the %i2." # %i1 = water source, %i2 = bucket
+ success_message: "You pour the %i1 into the %i2." # %i1 = water source, %i2 = bucket
```
### Multi-Piece Assembly (3+ items → 1)
@@ -227,7 +227,7 @@ craft:
message: "You try to puzzle how the pieces fit together."
- tick: 3
message: "Aha, this edge lines up here!"
- message: "You assemble the %n."
+ success_message: "You assemble the %n."
```
### Clean Recipes
@@ -245,7 +245,7 @@ craft:
ingredients:
- items: [grimy_guam]
quantity: 1
- # message omitted — uses default "You clean the %i1."
+ # success_message omitted — uses default "You clean the %i1."
# %i1 expands to the grimy herb name with its color
```
diff --git a/building_guide/rooms.md b/building_guide/rooms.md
index 0211c33..d3412de 100644
--- a/building_guide/rooms.md
+++ b/building_guide/rooms.md
@@ -42,6 +42,8 @@ Simple exit — always passable:
```yaml
exits:
north: 2
+ ne: 3 # ne/nw/se/sw also work
+ southeast: 4
```
Conditional exit — blocked until a world flag is set:
@@ -90,10 +92,11 @@ exits:
### Map grid & one-way exits
-Horizontal exits (north/south/east/west) must form a consistent 2D grid: from any
-starting room, walking N/S/E/W should never land two different rooms on the same
-spot, and a given room must always resolve to the same spot. Up/down don't move on
-the grid — they lead to a separate plane (floor) that is laid out on its own.
+All exits (north/south/east/west/ne/nw/se/sw) must form a consistent 3D grid: from
+any starting room, walking horizontal directions should never land two different
+rooms on the same 3D coordinate, and a given room must always resolve to the same
+spot. Up/down move on the z-axis within this same grid (different floors share the
+same x/y coordinate space).
Startup validation enforces this, starting from `startup_validation.root_rooms`
(see config.yaml). It reports an **overlap** (two rooms on one grid cell) or a
@@ -101,9 +104,10 @@ Startup validation enforces this, starting from `startup_validation.root_rooms`
Exits don't have to be reciprocal. A one-way link (e.g. room 2001 has `east: 2006`
but 2006 has no `west` back) renders on the map as a directional arrow
-(`← ↑ → ↓`, or `< ^ > v` in ASCII) instead of a two-way bar. If a link is open in
-one direction but blocked (failing condition) in the other, the open direction's
-arrow is shown; only a link with no traversable direction shows the blocked `X`.
+(`← ↑ → ↓`, or `< ^ > v` in ASCII, with `↗↖↘↙` for diagonal) instead of a
+two-way bar. If a link is open in one direction but blocked (failing condition) in
+the other, the open direction's arrow is shown; only a link with no traversable
+direction shows the blocked `X`. Blocked up/down exits also show the blocked `X`.
### Item Spawns — ground items that respawn