Merge pull request 'docs: economy v0.3 lockdown (custom mod + UI + tiers + plots)' (#63) from docs/economy-v0.3-lockdown into main

This commit was merged in pull request #63.
This commit is contained in:
2026-06-06 22:27:07 +00:00
+150 -54
View File
@@ -1,6 +1,6 @@
# Brass and Sigil — Economy & Quest System Design
> Status: architecture locked (v0.2). Implementation ready to begin.
> Status: architecture + UI approach locked (v0.3). Custom companion mod confirmed.
> Owner: matt
> Last updated: 2026-06-06
@@ -56,7 +56,7 @@ Each guild is a destination. The guild's NPC is both the **entry point** (accept
|---|---|---|
| **Adventurer's Guild** | Combat & exploration | Bounty board (daily mob hunts), boss-kill quests, dungeon-delve quests (future) |
| **Merchant's Bazaar** | Trade & raw-mat economy | Numismatics sell shop, dynamic exchange counter, player-driven job board |
| **Civic Office** | Land & status | Plot claim office, tier upgrades, sethome/warp services |
| **Civic Office** | Land & status | Tier upgrade screen, spawn plot registry (purchase / view your plots), sethome/warp services. NOTE: regular wilderness chunk claiming uses the FTB Chunks map and is tier-allocated, not paid per chunk — see §4. |
| **Library / Academy** | Knowledge & magic | FTB Quests anchor NPC, Ars Nouveau themed quests, lore terminals |
| **Tavern** | Social & onboarding | First-time newbie quests, casual NPCs, food/buff vendor |
| **Foundry / Workshop** | Crafting & commissions | Create-themed contracts, crafting orders, raw-material market |
@@ -73,7 +73,43 @@ Both pay into the same wallet. Players run the campaign at their pace and the da
---
## 4. Quest & bounty flow (universal pattern)
## 4. Tier system & spawn plots
Two distinct land/status systems that often get conflated. Keeping them clean:
### 4a. Civic tier ladder
Every player has a Civic rank. Higher rank unlocks perks. Players spend spurs at the Civic Office NPC to upgrade. Powered by FTB Ranks under the hood (permission nodes drive what each rank unlocks).
| # | Title | Cost to reach | Wilderness chunks claimable | Spawn plot slots | Sethomes | Daily bounty slots | Shop fee | Chat colour | Join broadcast | `/back` after death |
|---|---|---|---|---|---|---|---|---|---|---|
| 1 | **Peasant** | free (starter) | 9 | 0 | 1 | 3 | -0% | grey | no | no |
| 2 | **Citizen** | 500 | 25 | 1 | 2 | 3 | -0% | white | no | no |
| 3 | **Patron** | 2,000 | 60 | 1 | 3 | 4 | -2% | yellow | no | yes |
| 4 | **Notable** | 6,000 | 100 | 2 | 4 | 4 | -5% | green | simple | yes |
| 5 | **Baron** | 15,000 | 160 | 2 | 5 | 5 | -8% | cyan | simple | yes |
| 6 | **Noble** | 35,000 | 240 | 3 | 7 | 5 | -10% | purple | fancy | yes |
| 7 | **Lord** | 80,000 | 350 | 4 | 10 | 6 | -12% | gold | fancy | yes |
| 8 | **Sovereign** | 200,000 | 500 | 5 | unlimited | 6 | -15% | red | epic | yes |
Numbers are first-pass calibration. The full perk table lives in a single JSON (`config/bnstoolkit/tiers.json`) that's hot-reloadable via `/bnstoolkit reload`. Easy to tune any column without code changes.
**Wilderness claims:** at every tier above Peasant, you get a flat allowance of N chunks you can claim anywhere outside spawn via the FTB Chunks map. Claiming is **free** within your allowance, refused above. No per-chunk pricing. Driven by FTB Ranks → FTB Chunks permission nodes (`ftbchunks.max_claimed_chunks`).
### 4b. Spawn plots
Spawn plots are a **separate system** from wilderness claims.
- **Pre-defined regions** at spawn — single chunks or small fixed clusters — designated by admins as "plots." Visible as fenced/bordered areas on the spawn map.
- **Purchased with spurs** at additional cost per plot (separate from tier upgrade cost). Indicative pricing: standard plot ~2,000 spurs, premium (corner / prime location) ~5,000 spurs.
- **Primary use:** shops. Players set up Numismatics shop blocks on their plots and sell to other players. Residence is allowed but secondary.
- **Slot-limited by tier:** your civic rank determines how many spawn plots you can own simultaneously (column above). Hit the limit, you can't buy another until you upgrade or release a plot.
- **Purchase happens inside the FTB Chunks map UI** — clicking a plot region in the map opens a confirmation screen (provided by our custom mod's mixin) showing cost + your remaining slots. Same UI you use for wilderness claims, integrated.
- **Plot data lives in the custom mod** (`bnstoolkit:plots`), not in FTB Chunks. Plots are a separate ownership system that uses the FTB Chunks map as its visual surface.
---
## 5. Quest & bounty flow (universal pattern)
**Core principle:** for any guild, the player **accepts** work from an NPC, **completes** it in the world, then **returns** to that NPC to **turn it in** and claim the reward. No instant payouts. This:
@@ -120,31 +156,37 @@ The same accept → complete → return pattern works for every guild:
| **Library** | "Recover this lost tome" | find the book in a structure | NPC pays + grants reputation |
| **Foundry** | "Craft 10 Andesite Casings" | craft them | NPC pays commission |
### Player-facing tracking & cancellation (locked)
### Player-facing UI (locked)
Three surfaces, **all shipping together in Phase 3.** Not iterated, not optional.
Polished, integrated, no chat commands to memorise. All player interaction happens through GUIs and NPC dialogue. Custom companion mod (working name `bnstoolkit`) provides the screens; FTB Library's UI framework is the visual basis so our screens match FTB Quests, FTB Chunks, and FTB Teams natively.
| Surface | Role | Mechanism |
|---|---|---|
| **Bossbars** | Always-visible HUD — one bossbar per active quest, shows name + N/M progress bar | Vanilla `/bossbar` commands driven by KubeJS. Native per-player display (scoreboards are global; bossbars aren't). Up to 3 stacked at top of screen. |
| **`/quests` commands** | Management — list, inspect, cancel | KubeJS `ServerEvents.commandRegistry`. Works in chat and over the Telegram bridge. Clickable chat components for `[cancel]` and `[details]`. |
| **Easy NPC dialog** | Accept + turn-in at guild NPCs | Dialog action runs `/bns_quest accept <quest_id> <npc_tag>` (KubeJS-registered command). Dialog branching uses scoreboard objectives that KubeJS mirrors quest state into. |
| Command | Effect |
| Surface | Implementation |
|---|---|
| `/quests` | Lists your ACTIVE / READY quests with progress, source guild, reward |
| `/quests info <id>` | Detail view |
| `/quests cancel <id>` | Drops an active quest, frees the slot. Applies the same cooldown as if completed (prevents accept-cancel-accept RNG-shopping). |
| **Quest Log screen** | Custom mod screen. Tabs: Active / Available / Completed. Click a quest to inspect, cancel from the detail panel. Opened via keybind or by clicking a Quest Log block at any guild. |
| **Bounty Board screen** | Custom mod screen, opened by right-clicking the Adventurer's Guild Quartermaster NPC OR clicking the in-world Bounty Board block. Lists today's available daily bounties with descriptions, rewards, and "Accept" buttons. |
| **Tier upgrade screen** | Custom mod screen, opened at the Civic Office NPC. Visual ladder, your current tier highlighted, next-tier cost, perks unlocked at each rank, big Upgrade button. |
| **Plot purchase popup** | Custom mod mixin into the FTB Chunks map UI. Hover a plot region → cost + slots tooltip. Click → confirmation popup. Owned plots also clickable to see plot info. |
| **Shop browser** | Numismatics shop blocks render their existing inventory UI by default; optional richer browser screen for the central Merchant's Bazaar inventory. |
| **Quest progress HUD** | Custom mod render layer — styled HUD element showing active quest names + progress bars. NOT stacked vanilla bossbars. |
| **NPC dialogue + buttons** | Easy NPC handles all NPC interactions: accept/turn-in, info, tutorials, "click for details" buttons. Players learn the system through NPC dialogue, not by reading docs. |
### Why NOT FTB Quests for bounties
### Why custom mod, on FTB Library's UI framework
FTB Quests is the right tool for **progression** (Phase 5+), not for daily bounties. Confirmed via source review:
- **Visual consistency:** FTB Quests, FTB Chunks, FTB Teams all use FTB Library's widget framework. Our screens built on the same framework will look and feel like part of the same product.
- **Already a pack dependency:** no new mod added just for the UI layer.
- **Mixin compatibility:** our spawn plot mixin into the FTB Chunks map operates on FTB Library widgets natively — no translation layer between vanilla MC widgets and FTB Library widgets.
- **Less boilerplate than vanilla MC Screen API:** Panel, BlockButton, IconButton, Tooltip, TextField widgets already exist and behave consistently with how players already know FTB UIs to work.
- **Forking FTB is off the table:** FTB mods are "All Rights Reserved" — depending on FTB Library as a library is fine (that's what libraries are for), forking FTB Quests or FTB Chunks for redistribution is not legally clean. Custom mod alongside the FTB stack is the correct architecture.
- **No abandon/cancel event** — players can `Ctrl+Shift+R` to reset quest progress, but nothing fires that KubeJS can hook → can't enforce cancellation cooldown.
- **Cooldown is per-team, not per-player** — in a 4-player team, one member completing puts it on cooldown for all four.
- **No per-player quest visibility** — gating "5 of 20 active today" requires `CustomTask` gates rather than first-class per-player visibility.
### Why NOT FTB Quests for daily bounties
For long-form progression questing, all three are non-issues. So: FTB Quests for the campaign, custom KubeJS system for daily bounties.
FTB Quests stays for **long-form progression** (Phase 5+), not for daily bounties. Source review confirms:
- No abandon/cancel event (Ctrl+Shift+R reset fires no event we can hook)
- Cooldown is per-team, not per-player
- Visibility is per-team, not per-player — rotating "5 of 20 daily" doesn't fit cleanly
For long-form progression where one-shot rewards + team scope are fine, FTB Quests is great. Our custom bounty engine handles the daily/repeatable pattern with its own UI.
### Quest slot limit
@@ -297,10 +339,22 @@ A quest moving to READY frees the slot for accepting a new one even before turn-
|---|---|---|
| **FTB Quests** | 2101.1.25 | Progression quest UI (Phase 5+) |
| **FTB XMod Compat** | latest 1.21.1 NeoForge | KubeJS hooks for FTB Chunks claim events + FTB Quests events |
| **FTB Ranks** | 2101.1.3 | Tier system (Phase 6). CurseForge only, no Modrinth listing. |
| **FTB Ranks** | 2101.1.3 | Tier system. CurseForge only, no Modrinth listing. |
### Custom mod
**Not needed for V1.** Re-evaluate only if implementation hits a hard wall on a specific feature.
### Building our own (custom companion mod)
**`bnstoolkit`** (working name) — a small companion mod in our own repo. Confirmed locked-in.
- Provides all custom GUI screens (Quest Log, Bounty Board, Tier upgrade, Shop browser)
- Provides the FTB Chunks map mixins (spawn plot cost overlay, hover tooltip, purchase popup)
- Provides custom quest-progress HUD render layer
- Provides the `bnstoolkit:plots` data storage + ownership permissions
- Provides network packets for client↔server state sync
- Provides the `/bnstoolkit reload` admin command for hot-reloading tier config
- Built on FTB Library UI framework for visual consistency
- KubeJS handles all gameplay logic (bounty rotation, state machine, villager trades, Numismatics integration) — the mod is purely the UI + integration layer
Estimated scope: ~2-3k LOC, single-developer week of focused work. Bounded.
### Explicitly NOT adding
- CustomNPCs (Easy NPC covers it)
@@ -317,13 +371,14 @@ Each phase is independently shippable. Earlier phases unlock value without depen
| Phase | Deliverable | Spawn build required? |
|---|---|---|
| **0a** | **Mod additions PR:** FTB Quests + FTB XMod Compat + FTB Ranks (+ minor Easy NPC bump). New pack version. | No |
| **0b** | Spawn skeleton — 7 guild building blockouts (rough). **User does in-game when time permits.** Non-blocking for everything else. | Yes (user) |
| **1** | **Sell shop:** Numismatics shop blocks for diamonds (10 spurs) + netherite ingots (100 spurs). Lifetime-sale tracker for diminishing returns. | No — test anywhere, drop into Bazaar later |
| **2** | **Plot claim cost:** `FTBChunksEvents.before('claim')` deducts spurs. Free first 9 chunks, 50/chunk to 25, 200/chunk beyond. | No |
| **3** | **Bounty engine:** state machine + `/quests` commands + bossbar HUD + 3-slot cap. Daily quest pool with KubeJS-rotated dailies. NPC dialog hooks ready but inert until guild NPCs exist at spawn. | No (NPC layer activates once spawn is built) |
| **4** | **Villager rebalance:** strip vanilla, ship spur-priced trade table via `ServerEvents.villagerTrades`. | No |
| **5** | **Progression quest line:** FTB Quests anchor + first chapter. KubeJS rewards dispense spurs via Numismatics API. | No (anchor NPC at Library once spawn exists) |
| **6** | **Tier upgrades:** FTB Ranks integrated. `/tier upgrade` deducts spurs and promotes via `ftbranks add`. Rank perms gate FTB Chunks claim limits. | No |
| **0b** | Spawn skeleton — 7 guild building blockouts (rough). **User does in-game when time permits.** Non-blocking. | Yes (user) |
| **0c** | **`bnstoolkit` companion mod — scaffolding pass.** Mod project set up, FTB Library UI dependency wired, network packet plumbing, build/release scripts. No screens yet. | No |
| **1** | **Sell shop:** Numismatics shop blocks for diamonds (10 spurs) + netherite ingots (100 spurs). Lifetime-sale tracker for diminishing returns. KubeJS only, no mod work needed. | No |
| **2** | **Tier upgrade flow:** FTB Ranks integrated + KubeJS `/tier upgrade` command. **`bnstoolkit` Tier upgrade screen** wired to Civic Office NPC. Tier perks driven by `tiers.json`. | No |
| **3** | **Spawn plot system:** plot region registry in `bnstoolkit`, ownership tracking, FTB Chunks map mixin (cost overlay + purchase popup). | No |
| **4** | **Bounty engine:** state machine, KubeJS-rotated dailies, `bnstoolkit` Bounty Board screen + Quest Log screen + Quest progress HUD. NPC dialog hooks via Easy NPC. 3-slot cap. | No (NPC layer activates once spawn is built) |
| **5** | **Villager rebalance:** strip vanilla, ship spur-priced trade table via `ServerEvents.villagerTrades`. | No |
| **6** | **Progression quest line:** FTB Quests anchor + first chapter. KubeJS rewards dispense spurs via Numismatics API. | No (anchor NPC at Library once spawn exists) |
| **7** | **Dynamic exchange rates:** global supply-pool pricing for raw mats. | No |
| **8+** | Lootr dungeons, Foundry crafting commissions, deeper FTB Quests chapters, player-vs-player bounties (if wanted). | TBD |
@@ -348,41 +403,82 @@ Resolved before implementation:
| Question | Decision |
|---|---|
| Quest UI for bounties | Custom (bossbars + commands + Easy NPC) — NOT FTB Quests |
| Quest UI for bounties | **Custom mod with FTB Library UI widgets** — proper GUI screens, no chat commands |
| Quest UI for progression | FTB Quests |
| State storage | Per-player JSON in `world/data/bns_economy/` |
| Numismatics access | Direct Java via `Java.loadClass` |
| Chunk claim refusal | `FTBChunksEvents.before('claim')` with `event.setResult(...)` |
| Tier system | FTB Ranks + permission-driven chunk limits |
| Custom mod for V1 | No — only if a hard wall appears |
| Sethomes / warps | Paid services (`/sethome` 50 spurs, `/warp` 25 spurs, `/back` 10 spurs) |
| Daily quest count | 5 active at a time, refresh per-player 24h after last accept |
| Plot purchase UI | Custom mod mixin into FTB Chunks map — hover preview, click-to-buy popup |
| Tier upgrade UI | Custom mod screen at Civic Office NPC |
| State storage | KubeJS-managed per-player JSON for quest state; mod-managed for plot ownership |
| Numismatics access | Direct Java via `Java.loadClass` from KubeJS; via API directly from the mod |
| Wilderness chunk allowance | Tier-driven via FTB Ranks permission nodes — no per-chunk pricing |
| Spawn plots | Predefined regions, slot-limited by tier, individually purchased with spurs |
| Tier ladder | Civic: Peasant → Citizen → Patron → Notable → Baron → Noble → Lord → Sovereign (8 tiers) |
| Tier perks | JSON-configured (`config/bnstoolkit/tiers.json`), hot-reloadable |
| Custom mod | Confirmed. Built on FTB Library UI framework. Working name `bnstoolkit`. |
| Sethomes / warps | Tier-allocated count (not paid per use) |
| Daily quest count | Tier-driven (3 at Peasant, up to 6 at Sovereign), refresh per-player 24h after last accept |
| Emeralds | Retired as currency, retain as a trade material for villager-redirect trades |
| Fork FTB | Not needed — depend on FTB Library as a UI lib, FTB Chunks/Quests stay unmodified, integration via mixins + KubeJS hooks |
### Still to decide (non-blocking — pick during implementation)
- **PvP bounties** — out of scope for V1, revisit after V1 ships
- **Lootr** — add only when structured dungeons exist (Phase 8+)
- **Default-rank starting permissions** — to be set with the first FTB Ranks config pass
- **Default-rank starting permissions** — finalised when FTB Ranks config is written
- **Spawn plot pricing** — first-pass numbers (2,000 standard / 5,000 premium), tune in playtest
---
## 12. Implementation notes
- KubeJS scripts organized under `pack/overrides/kubejs/server_scripts/economy/`:
- `01_numismatics_api.js` — Java.loadClass wrapper helpers (read/deposit/deduct)
- `02_quest_state.js` — load/save `world/data/bns_economy/<uuid>.json`
- `03_bossbar_hud.js` — per-player bossbar lifecycle
- `04_commands.js` — `/quests`, `/bns_quest`, `/tier` registrations
- `05_bounty_engine.js` — Phase 3 quest engine
- `06_sell_shop.js` — Phase 1 shop block tracking + DR
- `07_plot_costs.js` — Phase 2 FTB Chunks event handler
- `08_villager_trades.js` — Phase 4 rebalance
- `09_tier_upgrades.js` — Phase 6 rank upgrades
- `99_dynamic_exchange.js` — Phase 7
- State data under `world/data/bns_economy/<uuid>.json` per player. Readable, easy to debug. Migration to SQLite considered if dataset grows beyond ~100 players.
- All NPC dialog trees authored in Easy NPC's in-game editor, exported as preset JSONs into `pack/overrides/world/datapacks/bns-fuel/data/easy_npc/`. Dialog `Command` actions call into `/bns_quest` namespace which routes to KubeJS handlers.
- Trade table for villager rebalance: single source file `08_villager_trades.js`. Each profession × tier has its own block. One file = one diff to review during balance passes.
### KubeJS scripts (gameplay logic)
Organised under `pack/overrides/kubejs/server_scripts/economy/`:
- `01_numismatics_api.js` — Java.loadClass wrapper helpers (balance / deposit / deduct)
- `02_quest_state.js` — load/save `world/data/bns_economy/quests/<uuid>.json`
- `03_commands.js` — admin commands (`/tier upgrade`, `/bnstoolkit reload`, debug)
- `04_bounty_engine.js` — daily rotation, state machine, KubeJS↔mod packet handlers
- `05_sell_shop.js` — Numismatics shop tracking + diminishing returns
- `06_villager_trades.js` — Phase 5 `ServerEvents.villagerTrades` rebalance
- `07_tier_perks.js` — FTB Ranks promote/demote, perk application
- `99_dynamic_exchange.js` — Phase 7 supply-priced market
### Custom mod codebase
Repo: separate (or sub-tree of main repo, TBD).
Modid: `bnstoolkit` (working name).
Package layout:
```
bnstoolkit/
├── client/
│ ├── screen/ QuestLog, BountyBoard, Shop, Tier, PlotConfirm (FTB Library subclasses)
│ ├── mixin/ ChunkScreenPanel (cost overlay + plot button), ChunkButton (hover tooltip)
│ ├── hud/ QuestProgressHud (custom render)
│ └── ClientEvents keybind reg, screen reg, mixin loader
├── server/
│ ├── packet/ OpenScreen, UpgradeRank, BuyPlot, ClaimBounty, etc.
│ ├── command/ /bnstoolkit reload (config refresh)
│ └── data/ PlotRegistry, PlotOwnership (saved with world data)
├── common/
│ ├── data/ TierConfig (JSON-loaded), BountyDefinition, QuestState mirror
│ └── BnsToolkit.java mod entry
└── config-defaults/
├── tiers.json copied to config/bnstoolkit/tiers.json on first run
└── plots.json spawn plot region definitions
```
Architecture doc (`docs/bnstoolkit-architecture.md`) covers package layout, screen UX sketches, network packet contract, mixin targets, KubeJS↔mod integration surface — to be written before mod work begins.
### State data
- Quest state: `world/data/bns_economy/quests/<uuid>.json`. Readable JSON, easy to debug.
- Plot ownership: persisted with world via the mod's `SavedData` (vanilla NeoForge persistence). Authoritative source of truth.
- Tier config: `config/bnstoolkit/tiers.json` shipped from `pack/overrides/defaultconfigs/bnstoolkit/tiers.json`. Hot-reloadable.
- Plot definitions: `config/bnstoolkit/plots.json` shipped similarly. Defines plot region bounds, type (standard/premium), prices.
### NPC dialog
Authored in Easy NPC's in-game editor, exported as preset JSONs into `pack/overrides/world/datapacks/bns-fuel/data/easy_npc/`. Dialog `Command` actions call `/bnstoolkit <verb> ...` which routes to either the mod (for screen-opening) or KubeJS (for state changes).
### Villager rebalance
Single source file `06_villager_trades.js`. Each profession × tier has its own block. One file = one diff per balance pass.
---