De beste roguelikes doden je niet alleen. Ze zorgen ervoor dat je wilt sterven.
Dat klinkt vreemd, maar iedereen die om middernacht een run heeft verloren en om 12:03 een nieuwe is gestart, kent het gevoel. De dood doet pijn. Je gezondheid zakt naar nul. Het scherm overspoelt met falen. Toch zweeft je vinger al boven de play-knop. Iets aan de afgelopen twintig minuten was belangrijk genoeg om het spel niet te kunnen verlaten waar het eindigde.
Dit is de "nog één run"-loop, en dat is niet toevallig. Het is ontworpen. Als je een roguelike of een andere game met permadeath bouwt, is je hele taak het balanceren van twee tegenovergestelde krachten. De speler moet genoeg verliezen om spanning te voelen. Ze moeten genoeg behouden om hoop te voelen.
De valuta van falen
In mijn laatste project, Neon Survivor, wilde ik precies die spanning creëren. Wanneer de speler sterft, verdwijnt alles wat tijdens de run is verzameld, behalve één ding: goud. Dat goud wordt automatisch opgeslagen. Terug in het menu geven ze het uit aan permanente upgrades. Daarna duiken ze er weer in, iets sterker dan voorheen.
Deze eenvoudige loop vormt de kern van de hele game. Zonder deze loop is de dood een punt. De speler stopt, omdat de laatste run niets heeft opgeleverd. Met deze loop is de dood een komma. De run werd een farming-trip. Het verlies doet pijn, maar het heeft ook betaald voor morgen.
De truc is simpel. Je houdt iets over, zelfs als je de rest verliest. De uitdaging is om ervoor te zorgen dat hetgeen je behoudt ertoe doet, zonder de uitdaging te vernietigen. Als de upgrades te zwak zijn, stopt de speler met geven om het spel. Als ze te sterk zijn, speelt het spel zichzelf. In beide gevallen stort de loop in.
Twee klokken, nul verwarring
Om dit goed op te bouwen, moest ik twee aparte tijdlijnen beheren.
De Run-klok wordt gereset elke keer dat je op play drukt. Het houdt de gezondheid, de huidige score, het aantal vijandengolven en alle tijdelijke power-ups bij die tijdens de sessie zijn opgepakt. Wanneer het personage sterft, wordt deze klok teruggezet naar nul.
De Meta-klok wordt nooit gereset. Deze houdt het totale goud bij dat in elke poging is verdiend, de hoogste golf die ooit is bereikt en elke gekochte permanente upgrade. Deze klok blijft doortikken, ongeacht hoe vaak de browser wordt vernieuwd.
Meng deze twee en je krijgt bugs die moeilijk te traceren en pijnlijk om op te lossen zijn. Ik heb ontwikkelaars gezien die per ongeluk de voortgang van spelers wissen tijdens een routineuze scene-reset, omdat een cleanup-functie de verkeerde datastore raakte. De data van de Meta-klok verdampt. De speler keert terug naar nul goud en nul upgrades. Op dat moment is de relatie tussen jou en je speler verbroken. Ze beginnen niet aan een nieuwe run; ze beginnen aan een nieuwe vete.
De klokken gescheiden houden is niet alleen een stijlkeuze. Het is een overlevingsstrategie.
Hoe Phaser v4 de splitsing afhandelt
Ik heb Neon Survivor gebouwd in Phaser v4, dat twee specifieke tools biedt voor dit probleem.
De Registry houdt live data in het geheugen voor de huidige sessie. Het is snel. Het is simpel. Het verdampt echter op het moment dat de speler de pagina vernieuwt.
LocalStorage slaat gegevens op in de browser zelf. Het overleeft het sluiten van tabbladen, het herstarten van de browser en stroomuitval. Het is ook langzamer en minder betrouwbaar. Browsers kunnen het blokkeren, beperken of wissen als de opslagquota vol raken.
Mijn ontwerpkeuze was strikt. De Registry is de enige bron van waarheid tijdens het spelen. De game leest ervan, schrijft ernaar en vertrouwt er volledig op. LocalStorage fungeert niet als co-auteur. Het fungeert als een spiegel.
Dit is hoe de flow werkt. De game schrijft een aankoop van een upgrade naar de Registry. Een enkele manager-class houdt de Registry in de gaten. Wanneer gepast, spiegelt die manager de Registry-data naar LocalStorage. Als de browser het schrijven blokkeert, hapert de game niet. Als de opslag faalt, draait de huidige sessie nog steeds perfect. De speler kan alleen voortgang verliezen als ze het tabblad in exact hetzelfde seconde sluiten, maar de sessie zelf crasht nooit.
Dit patroon voorkomt een subtiele ramp. Als je elk systeem rechtstreeks naar LocalStorage laat schrijven, creëer je afhankelijkheden van een fragiele API. Een speler met privacy-instellingen die hoog staan afgesteld of een apparaat met weinig opslagruimte, zou kunnen merken dat de game vertraagt of bevriest tijdens het gevecht omdat een achtergrondfunctie probeerde statistieken op te slaan. Door de Registry de enige bron van waarheid te maken, houd je de actie snel en het risico beperkt.
Laat de code ademen
Ik heb ook events gebruikt om de systemen te ontkoppelen. Wanneer een run eindigt, regelt de GameScene niet zijn eigen begrafenis. Het roept geen save-functie aan. Het importeert geen storage-utility. Het zendt simpelweg een "run-ended" event uit met een payload van de relevante data.
A separate listener handles the bookkeeping. It receives the event, updates the Meta Clock, and tells the manager to mirror the new totals to LocalStorage.
This separation pays off immediately. I can rewrite the entire GameScene, swap out the player character, change the camera angle, or even shift the genre from survival to bullet hell without touching the save system. The systems are independent. They talk through events, not direct function calls. That means fewer merge conflicts, fewer bugs, and a codebase that does not turn into spaghetti after six months.
Upgrades That Change the Game
Having a technical backbone is useless if the rewards feel like a spreadsheet. I spent a lot of time on how upgrades actually feel to play.
Some upgrades are safe. Extra movement speed. Bonus health. Faster reload. These give the player more room for error. They are comforting. They shrink the game without changing its rules.
Other upgrades rewrite the rules entirely. In Neon Survivor, I added "Piercing Rounds." Before this upgrade, a bullet stopped on the first enemy it hit. After the upgrade, it punches through enemies, potentially clearing entire lines in a single shot.
The difference is dramatic. Speed and health might let you survive longer, but Piercing Rounds changes how you position yourself. You start lining up enemies. You stop kiting around the edges and start cutting through the center. The decision space of the game expands.
Good progression should change a player's decisions, not just increase their numbers. If every upgrade is a percentage bump, the player stops reading the descriptions. They click, they upgrade, they forget. If an upgrade makes them rethink their strategy, they remember it. They talk about it. They come back to see what else might flip the game on its head.
The Real Payoff
The "one more run" loop is not a single system. It is a relationship between loss and gain, built on clean architecture and meaningful rewards.
Build two distinct timelines and protect the Meta Clock like it holds your players' trust, because it does. Use your engine's tools to keep live data fast and persistent data safe. Decouple your scenes from your storage so you can iterate without fear. And when you design upgrades, ask whether they give the player more time, or more interesting choices.
Get this right, and your players will not just tolerate death. They will depend on it. Every run becomes a down payment on the next one. The game stops being a series of restarts and becomes a single, continuous climb.
