explodorama / commit
Plan: drop the Workshop and Keep or Fresh
PLAN.md | 143 ++++++++++++++++++------------------------------------- README.md | 2 +- decisions.md | 25 +++++++++- src/sim/state.ts | 4 +- src/sim/types.ts | 2 +- 5 files changed, 74 insertions(+), 102 deletions(-) diff --git a/PLAN.md b/PLAN.md index 3fcaf81..c24cf0f 100644 --- a/PLAN.md +++ b/PLAN.md @@ -20,9 +20,9 @@ turn), §15 (notes for the implementer) and §18 (milestones). Reasons for decis | 4 | Undo | **None.** | | 5 | Which actions | **All actions named in this plan** (§3), plus any agreed later. | | 6 | Name | **Explodorama.** ("Bomberman" is a Konami trademark — never use it in the UI, title, manifest or repo name.) | -| 7 | Shop purchases | **Last for the current run only.** Permanent progress comes from the Workshop (§7), which is a later milestone. | -| 8 | Permanent upgrades | **Workshop between runs** (Everspace-style): coins are deposited into upgrade tracks whose tiers cost 5, 10, 15, … coins. See §7. | -| 9 | Death | **The player chooses** after each death: **Keep** (keep Bomb+, Fire+, Run) or **Fresh** (lose them, get coins). Balanced so most players would pick each about half the time. See §9. | +| 7 | Shop purchases | **Last for the current run only.** Nothing carries over from one run to the next. | +| 8 | Permanent upgrades | ~~Workshop between runs~~ *Dropped 2026-10-24 (user's call): permanent upgrades across runs would ruin the game; every run stands alone.* See §7. | +| 9 | Death | ~~Keep or Fresh~~ *Dropped 2026-10-24 (user's call):* no choice and no payout. A death with lives left retries the level as it was, keeping what the run had; nothing is gained by it but what the player learned. See §9. | | 10 | Curses | **Exist, but only appear after the first shop** (level 2 onward). See §6. | | 11 | Reapers / turn limit | **Later** (post-MVP). The par-turn coin bonus stays. | | 12 | Run length | **50 levels with an ending**, like the NES. A win produces a **victory certificate with a QR code** for that seed. See §11. *Changed 2026-10-23 (user request): 20 levels, on the one 9 × 11 board.* | @@ -75,17 +75,15 @@ Rules that fall out of this: | Stat | Start | Notes | |---|---|---| -| Lives | 3 | Shop and Workshop can add more. | +| Lives | 3 | The shop can add more. | | Bomb capacity | 1 | Max own bombs on the board at once. | | Fire (blast radius) | 1 | Tiles in each of 4 directions. | | Fuse | 3 | Starting timer of the player's bombs. | | Abilities | none | From pickups or the shop (§3.2, §5). | | Charges | none | Temporary changes dropped by enemies, working on pickup (§3.3). | -| Coins | 0 | Spent in the shop (§8); leftovers go to the Workshop (§7). | +| Coins | 0 | Spent in the shop (§8). | | Curse | none | At most one active at a time (§6). | -Starting values can be raised by Workshop tiers (§7). - --- ## 3. Actions @@ -243,7 +241,7 @@ Additions: NES rules kept (they create the classic tension): -- **One pickup per level** under a soft block (more via shop/Workshop upgrades), plus the +- **One pickup per level** under a soft block (more via shop upgrades), plus the **exit door** under another soft block. *Since 2026-10-23 (user request) the pickup is a **gem** that offers a choice:* taking it offers `OFFER_SIZE` (5) different power-ups, drawn by the weights below without repeats and leaving out abilities and passes already held, and @@ -265,8 +263,8 @@ NES rules kept (they create the classic tension): Bomb+ 20, Fire+ 20, Fuse+ 6, Coin bag 12 (10 coins), Heart 4, Wall Pass 8, Bomb Pass 8, Flame Pass 5, Detonator 9, Star 8 (8 turns), and since 2026-10-22 Kick 8, Throw 8, Teleport 3; since 2026-10-23 Run 10, and they weight the gem's offer (`POWER_UP_WEIGHTS` in `sim/turn.ts`). Sprites: §13 (since 2026-10-22, a bomb or the astronaut with a - modifier badge for Bomb+, Fire+, Fuse+, Run, Kick and Throw; gems before). Until Keep / Fresh exists, a death keeps stats, every power-up and pass (since 2026-10-23, user request; before, "as Keep" - would). A Run collects what is on the tile it passes through. + modifier badge for Bomb+, Fire+, Fuse+, Run, Kick and Throw; gems before). A death keeps stats, every power-up and pass (since 2026-10-23, user request; the planned Keep / Fresh choice was dropped + 2026-10-24). A Run collects what is on the tile it passes through. --- @@ -293,13 +291,9 @@ The user wants to start thinking about making power-ups **exclusive**: picking o **Inconsistencies with the current plan, to resolve before building** (CLAUDE.md asks to raise these, not paper over them): -1. **Keep / Fresh on death (§9)** is balanced around *accumulated* stats and abilities - ("Keep: 💣2 🔥3 Run"). With slots, "Keep" keeps the slot loadout; Fresh's payout formula - would need rethinking. +1. ~~**Keep / Fresh on death (§9)**~~ — dropped 2026-10-24. 2. **The shop (§8)** sells abilities and stats; with slots, a purchase may also force a swap. -3. **The Workshop (§7)** has tracks like "Bomb satchel +1 starting capacity" and "Run from - the start" — they'd become starting slot contents or extra slots ("+1 slot" is a natural - Workshop track). +3. ~~**The Workshop (§7)**~~ — dropped 2026-10-24. 4. **NES rule: passes and Detonator are lost on death (§5, §9)** — with slots, perhaps nothing is lost on death and the slot choice itself is the cost. *Settled 2026-10-23 (user request): nothing is lost on death, slots or not.* @@ -331,41 +325,18 @@ gone or left on the tile? Should action charges (one-use, from enemies) stay sep | **Heavy Feet** | Run is disabled. | | **Damp** | Fire is 1. | -- **Cures:** wait it out, a Star, or the shop's **Cleanse** charge. Workshop track - **Curse Ward** makes the first skull per level harmless. +- **Cures:** wait it out, a Star, or the shop's **Cleanse** charge. - (Open, §14: should skulls also give coins — a risk-for-reward choice?) --- -## 7. The Workshop (permanent upgrades between runs) — later milestone - -Like *Everspace*, where you spend between runs on more weapon slots or stronger shields. +## 7. ~~The Workshop~~ — dropped (user's call, 2026-10-24) -- **Coins left over at the end of a run** (win or lose) are banked into the Workshop. - (Open, §14: leftover only, or all coins earned?) -- The Workshop has **upgrade tracks**. Each track has tiers; **tier n costs 5 × n coins** - (5, 10, 15, 20, …). Coins can be **deposited partially** — a track shows a progress bar toward - its next tier, so even a short run moves something forward. -- Tracks (each capped; values to tune): - -| Track | Per tier | Cap | -|---|---|---| -| Extra life | +1 starting life | +2 | -| Bomb satchel | +1 starting bomb capacity | +2 | -| Gunpowder | +1 starting fire | +2 | -| Shop shelf | +1 offer per shop | +2 | -| Haggler | 1 free reroll per shop | 1 | -| Charge pouch | Start each run with 1 random action charge | +3 | -| Lucky | +5% drop chance | +3 | -| Purse | Start each run with +5 coins | +3 | -| Prospector | +1 hidden pickup per level | +1 | -| Curse Ward | First skull per level is harmless | 1 | -| Run from the start | Start with Run | 1 | - -- Workshop state lives in `localStorage` (try/catch — it can be unavailable). Offer - **export/import** of the save as text, because phones clear site data. -- The Workshop loadout at run start is part of the run record (§11) — it changes the - starting state, so replays and certificates must include it. +The plan had permanent upgrades between runs, Everspace-style: coins left over at the end of a +run banked into upgrade tracks (more lives, bombs or fire to start with, Run from the start, …). +Dropped: the user can't imagine cross-run permanent upgrades that wouldn't ruin the game. Every +run starts the same; what a run gains, it keeps only until it ends. (The tracks and their costs +are in git history and decisions.md.) --- @@ -385,37 +356,23 @@ Like *Everspace*, where you spend between runs on more weapon slots or stronger --- -## 9. Death: Keep or Fresh +## 9. Death *Built 2026-10-24 (user request):* the death banner (and the game-over one) says how and where the player died — level, turn, and the cause (`GameState.death`): walked into an enemy, an -enemy walked in, a bomb's blast, a chain reaction's second bomb, or last turn's flame. - -When the player dies with lives left, the level will restart from its seed (same layout, -enemies reset). Before that, a choice screen with two buttons, **both showing exact numbers**: - -| | **Keep** | **Fresh** | -|---|---|---| -| Bomb +, Fire +, Fuse +, Run | kept | **reset to starting values** | -| Wall Pass, Bomb Pass, Flame Pass, Detonator, Star | lost (NES rule) — ***open:** since 2026-10-23 a death keeps them (user request), so this row, and what Keep vs Fresh costs, needs rethinking before §9 is built* | lost | -| Coins | kept | kept, **plus a coin payout** | -| Action charges | kept | kept | -| Curse | removed | removed | - -Example buttons: "**Keep** — 💣2 🔥3 Run" / "**Fresh** — +14 coins". - -**Fairness (target: most players pick each about half the time).** The trade-off is -*power now* vs *coins*, and coins are worth more than their shop price because leftovers become -**permanent Workshop progress** (§7). Starting formula, to tune by playtesting: +enemy walked in, a bomb's blast, a chain reaction's second bomb, or last turn's flame — and +replays the player's own last turns (§13c). - payout = round(0.75 × shop value of everything Fresh resets) + 3 +A death with lives left restarts the level from its seed: the same layout, the enemies back where +they started, and the player keeping everything the run had (stats, power-ups, passes, charges, +coins; since 2026-10-23). At game over, **Same dungeon** runs the same seed again from level 1, +with nothing carried over, and **New dungeon** a new one. -- The flat +3 keeps Fresh meaningful early, when there's little to give up. -- The 0.75 factor means Fresh never fully refunds the run's power, so it's not a free win late. -- **Measuring balance:** the app has no backend or telemetry (on purpose). Record each choice in - local stats (shown on the run summary and in a dev overlay `?debug=1`), and use playtests. -- Coins collected during the failed attempt are kept either way. -- (Open, §14: should Fresh also re-roll the level layout?) +~~**Keep or Fresh**~~ — *dropped 2026-10-24 (user's call).* The plan was a choice after each +death: keep the run's power, or reset it for a coin payout, balanced so each was picked about half +the time. Now there is no choice and no payout: a retry, of the level or of the whole dungeon, is +just another try at the same board, its only benefit what the player now knows. (The table and +the payout formula are in git history and decisions.md.) --- @@ -476,11 +433,11 @@ design; the board code for them was removed. 50 + 10 × enemies, bonus 5 coins; the HUD shows `turn / par`. (Turn **limit** with Reapers: later milestone.) - **50 levels**, difficulty rising through enemy count, types, speed and soft-block density. -- **Game over** at 0 lives → run summary (level reached, coins banked, kills, Keep/Fresh choices, - seed) → Workshop → new run. +- **Game over** at 0 lives → run summary (level reached, coins, kills, seed) → the same dungeon + again or a new one. - **Ending** after level 50: an ending screen, then the **victory certificate**. - **Mid-run save is required**, not optional: a 50-level run won't happen in one sitting on a - phone. The save is just the run record (seed + Workshop loadout + action log, §12), replayed on + phone. The save is just the run record (seed + action log, §12), replayed on load — or a JSON snapshot of the state plus the log so far. *Built (2026-10-20):* the record, in `localStorage`, after every action, replayed on load; only for the same `SIM_VERSION`, and never for test URLs (`?seed`, `?level`, `?charges`). Finished runs aren't resumed. @@ -496,7 +453,7 @@ no certificate, nor any other achievement. A **Developer** run earns them all, but each shows a **red border** (user request, 2026-10-23, "like the red quarters some bars used in jukeboxes"); its victory banner is framed in red already. -Shows: **seed, date, turns, deaths, Keep/Fresh choices, Workshop loadout, sim version**, and a +Shows: **seed, date, turns, deaths, sim version**, and a **QR code** linking to `https://pavelsafronov.gitlab.io/explodorama/#cert=…`. Being honest about what this can prove: the game is fully client-side and open source, so any @@ -652,7 +609,7 @@ Sprite assignments (✅ = drawn now; the rest are copied and waiting for their f The pack has more enemies (bee, ladybug, snail, worm, barnacle, fish, spiked slime, falling block) and more tiles (keys, locks, levers, spikes, torches, …) for later enemies, curses and -actions; copy them in when they are used. Icons the pack doesn't have (shop, workshop, trophy, +actions; copy them in when they are used. Icons the pack doesn't have (shop, trophy, settings, sound, and most action charges) are still open. --- @@ -808,7 +765,7 @@ parameters: `?dev`, `?immortal`. | ~~**Board: Normal**~~ | *Removed 2026-10-23.* 31 × 13, density 35%, 50 levels, enemies 3 + 1 per 3 levels (max 10), par 50 + 10/enemy. | | ~~**Board: Small**~~ | *Now the only board (no longer an option).* 9 × 11 (fits a phone whole; the camera scales to fit both ways, no scrolling), density 25%, **20 levels**, enemies 2 + 1 per 4 levels (max 5), par 25 + 8/enemy. Same enemy-type schedule. Levelgen tops up crates if fewer than 2 are far enough for the exit and power-up. | | **Developer** | *Since 2026-10-23 (user request), only this:* an **extra** gem (`PowerUp.extra`; since 2026-10-24 a turning, glittering rainbow gem offering every power-up not held yet and every charge) lies right of the start, every level and after every death, to try the choice at once; the level keeps its own gem, hidden as usual (at first it was that gem, moved). Achievements count, with a red border (the victory banner is framed in red). (Until then: every ability and pass, 5 bombs, blast 5, unlimited charges shown as ∞; **killable**, split from Immortal by the user.) | -| **Immortal** | The player can't be hurt at all, so the run can be played to the end — but **an Immortal run earns no achievements** (the victory certificate, the Workshop's rewards, when they exist). | +| **Immortal** | The player can't be hurt at all, so the run can be played to the end — but **an Immortal run earns no achievements** (the victory certificate, when it exists). | | ~~**Crumbling crates**~~ | *Always on since 2026-10-23 (no longer an option).* When the last enemy dies, every crate gets a countdown of 1–3 turns (seeded, `hash(seed, "crumble", level)`), shown by shaking and fading; at 0 it is gone, revealing whatever was under it. It is not flame: no punishment, nothing burned. | URL test parameters `?dev` and `?immortal` set them for a test board. @@ -817,13 +774,9 @@ URL test parameters `?dev` and `?immortal` set them for a test board. ## 14. Open questions -1. **Workshop banking:** only coins **left over** at the end of a run, or **all** coins earned? - *Recommendation:* left over — it creates a real "spend now or bank it" choice in every shop. -2. **Workshop deposits:** is "tier n costs 5 × n, deposit partially with a progress bar" the - right reading of "put 5/10/15 coins into a permanently-increasing slot"? -3. **Fresh start and the level:** should Fresh also **re-roll the level layout** (a new board as - well as new pockets)? *Recommendation:* yes, it gives Fresh a feel of its own. It stays - deterministic (the attempt number goes into the levelgen stream). +1. ~~**Workshop banking**~~ — no Workshop (dropped 2026-10-24, §7). +2. ~~**Workshop deposits**~~ — no Workshop. +3. ~~**Fresh start and the level**~~ — no Keep / Fresh (dropped 2026-10-24, §9). 4. **Skulls with coins:** should a skull also give coins, making it a risk-for-reward choice rather than only something to avoid? *Recommendation:* yes, a small amount. 5. **Level width ramp:** start narrower (e.g. 15 columns) and grow to the full 31 by ~level 10, @@ -836,7 +789,7 @@ URL test parameters `?dev` and `?immortal` set them for a test board. 8. **Board theme:** ~~light "paper" board or dark board?~~ Settled by the Kenney art (2026-10-20): a pale sky-blue board under dark bars, coloured as the sprites are. 9. **Exclusive power-ups (§5b):** slots instead of collecting everything? How many, and what - takes one? Needs answers before the shop and Keep / Fresh are built, since both depend on it. + takes one? Needs answers before the shop is built, since it depends on it. 10. **Enemies sharing a tile:** they do now, as in the NES original (as far as remembered). Should they block each other instead? @@ -861,14 +814,14 @@ URL test parameters `?dev` and `?immortal` set them for a test board. recompute on resize/orientation change. - **Keep LittleJS out of `sim/`.** If a test needs to import LittleJS, the boundary is wrong. - **Record the run from day one.** Every input that changes state — actions, shop purchases, - rerolls, Keep/Fresh, Workshop loadout at start — goes through `sim/` and is appended to the run + rerolls — goes through `sim/` and is appended to the run record. That one log gives mid-run save, replays and certificates. - **Test priorities** (Vitest): turn phase order; bomb timer semantics (not ticked on placement turn); chain reactions; flame stops at walls and destroys the first soft block; Pierce/Power; Run needs both tiles free; Kick slide stop; enemy blocked by a bomb placed this turn stays put; contact checks including swaps; levelgen invariants across many seeds; danger overlay matches what `step()` actually does (predict → step → compare); **replay determinism** (record a random - run, replay it, identical final state and hash); Keep/Fresh payout formula; curses never before + run, replay it, identical final state and hash); curses never before the first shop. - **Screenshots:** Playwright at a phone viewport (e.g. 390×844) and desktop, with URL params like `?seed=123&level=1` for reproducible scenes. The user reviews them before any commit. @@ -899,8 +852,6 @@ src/ danger.ts predicted flame tiles this turn / next turn curses.ts shop.ts offers, prices, purchase - death.ts Keep / Fresh options and payout - workshop.ts tracks, tiers, deposits record.ts run record, replay, hash, SIM_VERSION render/ LittleJS board.ts sprites, highlights, danger overlay, intents @@ -908,7 +859,7 @@ src/ effects.ts turns a turn's events into short animations (appear, slide, swell, go away); no input lock — see decisions.md 2026-10-22 camera.ts - ui/ DOM: action bar, HUD, shop, death choice, Workshop, certificate, About + ui/ DOM: action bar, HUD, shop, death choice, certificate, About audio.ts Kenney pack sound effects (§13); ZzFX for any it lacks persist.ts localStorage save/load, export/import main.ts @@ -947,8 +898,8 @@ tools/ compose-icons.sh (composed sprites and the app icons), sc - `.gitlab-ci.yml`: copy nordic-skating's (test stage, then `pages` with `mv dist public` and the "fail loudly" checks; add a check that the sprites were built). Project at `gitlab.com/PavelSafronov/explodorama`, served at `https://pavelsafronov.gitlab.io/explodorama/`. -- Docs to create and keep current: `README.md` (how to play; every action, pickup, curse, enemy, - Workshop track; Attribution), this `PLAN.md`, `decisions.md` (each decision + why — seed it +- Docs to create and keep current: `README.md` (how to play; every action, pickup, curse, enemy; + Attribution), this `PLAN.md`, `decisions.md` (each decision + why — seed it from §0), `design.md` (balance tables: enemy schedule, prices, drop rates, payout formula). --- @@ -971,13 +922,13 @@ tools/ compose-icons.sh (composed sprites and the app icons), sc tap far = auto-move (§3.1). 7. **M6 – Run loop:** ✅ NES pickups (all 11, one hidden per level, Run on level 1 or 2; since 2026-10-23 a gem offering 5 to choose from, no Run guarantee), Run and Detonate, the passes and Star, 50-level progression and ending, mid-run save - (2026-10-20). ⏳ Shop after each level, Keep/Fresh death choice, curses from level 2. + (2026-10-20). ⏳ Shop after each level, curses from level 2. (The Keep/Fresh death choice was dropped 2026-10-24.) 8. **M7 – Look & feel:** ✅ animations (2026-10-22: everything that appears, moves, changes or goes away on the board, the top bar's numbers, the banner, and dialogs opening and closing); ✅ installable with offline play (2026-10-23); ✅ the demo before the game (2026-10-23, §13a); ⏳ sounds (Kenney pack, §13), remaining enemies and actions, screenshots tool. -9. **M8 – Permanence:** Workshop, save export/import, victory certificate + QR, replay file and - verify page. +9. **M8 – Records:** save export/import, victory certificate + QR, replay file and verify page. + (The Workshop was here until 2026-10-24: dropped, §7.) 10. **Later:** Reapers + turn limit, daily seed, final art. ### Backlog diff --git a/README.md b/README.md index 0fdc256..579975e 100644 --- a/README.md +++ b/README.md @@ -8,7 +8,7 @@ what will burn before you commit. Status: **early development.** The board, bombs, lives, the first three enemy types, coins, all seven charges that work when picked up, a hidden gem on every level that offers a choice of power-ups, the exit, the 20-level run with its ending, and saving -mid-run work. The shop, the Keep / Fresh choice on death, curses and more enemies are planned — +mid-run work. The shop, curses and more enemies are planned — see [PLAN.md](PLAN.md). Version: **24**, shown at the bottom of the menu with the commit the game was built from (a link diff --git a/decisions.md b/decisions.md index d880bdb..4d07a1d 100644 --- a/decisions.md +++ b/decisions.md @@ -14,8 +14,8 @@ in [PLAN.md](PLAN.md); this file records the reasoning so it isn't lost. 6. **Name: Explodorama.** "Bomberman" is a Konami trademark and must never appear in the game. 7. **Shop purchases last for the current run only.** 8. **Permanent upgrades come from a Workshop between runs** (Everspace-style tracks, tier n costs - 5 × n coins). Later milestone. -9. **On death the player chooses Keep or Fresh**, balanced so each is picked about half the + 5 × n coins). Later milestone. *Dropped 2026-10-24 (see that day's entry).* +9. *(Dropped 2026-10-24, see that day's entry.)* **On death the player chooses Keep or Fresh**, balanced so each is picked about half the time. See PLAN.md §9. 10. **Curses only appear after the first shop.** 11. **Reapers and the turn limit come later.** @@ -1598,3 +1598,24 @@ step and before auto-move's walk: the tile where a slide stops, with Slide held, tile that is also a teleport target still slides only if picked with Move (there a teleport wins, being safe); with nothing picked, a tile you can walk to was never a teleport anyway. The demo's slide scene now shows the plain tap (its caption: "tap where you stop"). + +### 2026-10-24 — No Workshop + +User's call: drop the Workshop, the permanent upgrades between runs planned since the start +(decision 8): "I can't imagine cross-game permanent upgrades that wouldn't ruin the whole thing." +Every run now starts the same, and nothing a run gains outlives it. Nothing of it was built; the +plan's mentions are gone (PLAN.md §7 says why). One knock-on, flagged to the user: Keep or Fresh +(§9) was balanced on coins being worth more than their shop price, as leftovers would become +Workshop progress; without it, Fresh's coin payout needs another look when §9 is built. Leftover +coins at the end of a run now count only on the high-score board. + +### 2026-10-24 — No Keep or Fresh; nothing carried between runs + +User's call, on the flag raised with dropping the Workshop: no leftover coins carry over between +runs, and a retry — "fresh or re-run" — is just another try at the same board, "no added benefit +(except their knowledge)". So the Keep or Fresh choice after a death (decision 9: keep the run's +power, or reset it for a coin payout) is dropped too, with its payout formula and its open +questions. What is built already matches: a death with lives left restarts the level from its +seed with everything the run had, and game over's Same dungeon starts the seed again from level +1 with nothing carried over. The rest of the plan no longer mentions it (§0, §5, §5b, §9, the run +summary, the certificate, §14, the architecture and the milestones). diff --git a/src/sim/state.ts b/src/sim/state.ts index b70cb5e..779776c 100644 --- a/src/sim/state.ts +++ b/src/sim/state.ts @@ -78,8 +78,8 @@ export function createLevel(seed: number, level: number, options: RunOptions, ca /** * What the player takes on, to the next level or the retry after a death: everything. Since * 2026-10-23 (user request) a death costs no power-ups; the NES rule lost the passes, Detonator - * and Star. (A Star can't be running at a death: nothing hurts the player while it lasts.) - * (The Keep / Fresh choice of PLAN.md §9 will decide about the stats and Run.) + * and Star. (A Star can't be running at a death: nothing hurts the player while it lasts.) There + * is no Keep / Fresh choice (dropped 2026-10-24, PLAN.md §9): a retry is the same try again. */ export function carryOf(s: GameState): Carry { return { diff --git a/src/sim/types.ts b/src/sim/types.ts index 069c30c..a4d0ffe 100644 --- a/src/sim/types.ts +++ b/src/sim/types.ts @@ -69,7 +69,7 @@ export interface RunOptions { /** * Immortal: nothing can kill the player, so the run * can be played to the end — but it earns no achievements (when they exist: the victory - * certificate, the Workshop's rewards). + * certificate). */ immortal: boolean }