A pixel-art colony-survival game about a family rebuilding after losing everything. By DeadlyDog Productions. Free to play in a browser, no account, no install:
▶ Play it
Hamburg, 1683. Your father is executed for "malicious affairs", your name is taken with him, and you and your sister run through the marsh gate before they can take you too. Deep in the woods you find a clearing, and in it a burned cabin. Everything after that is yours.
New: Forester: Reckoning — the same story lived in first person, in 3D. Its code lives in
reckoning/; seereckoning/models/README.mdfor replacing its models with ones made in Blender, andreckoning/tools/export_site.pyfor copying it onto the studio website.
A colony sim that cares more about people than about production lines. Everyone in it has a temperament, a creed, a trade they are getting better at, opinions about the others, and a memory. They fall out. They grieve. They freeze if you have not built a roof.
Around your clearing is the whole of Europe on the same map — zoom out far enough and the ground gives way to the continent, with its crowns going to war, seizing each other's land, and eventually noticing you. You can chart it, trade with it, put agents in its cities and march on them.
- The colony — fell, build, farm, bake, forge, mine, smelt, wall the town
- The people — recruit wanderers at the gate by talking them round, appoint mayors to run daughter towns, keep them fed, housed, paid and at peace
- Faith and law — proclaim a creed or don't, set taxes, write edicts, and live with what that does to the people who disagree
- The world — a live Europe of a hundred-odd cities, trade pacts you have to negotiate and then keep, scouts, spies, war parties and sieges
- The end — a reckoning you can call whenever the ambitions are in hand
Six save slots, and a colony can be written out to a file you keep.
There is no build step and there are no dependencies. It is HTML, CSS and JavaScript, served as files.
python3 -m http.server 8181
Then open http://localhost:8181. That is the whole of it.
It does have to be served, not opened as a file:// — the game recolours
sprites at load (this is how a regiment gets its coat colour) by reading pixels
back out of a canvas, and a canvas that has had a file:// image drawn into it
refuses to be read. Any static server will do.
index.html |
every panel and screen in the game |
game.js |
the whole game — world, simulation, render, UI, saves |
sfx.js |
sound and music, synthesised at runtime; no audio files |
forester-ui.css |
one stylesheet, with its design tokens at the top |
assets/sprites/ |
the finished sprites the game loads |
art/prompts/ |
the prompt each piece of art was generated from |
tools/ |
the art pipeline, and a few dev helpers |
A few things worth knowing before changing it:
- The world is generated, not stored. Terrain comes out of a seeded chunk generator; saves keep only the differences — which trees you felled, what you built. That is why a save is 60KB and not 6MB.
- Sound is synthesised. There is not one audio file in the repository. Every axe, bell, musket and bar of music is Web Audio, built at runtime.
- Art is generated through
tools/.gen_art.pysends a prompt fromart/prompts/to Gemini;pixelate.pycrushes the result down to a true low-resolution sprite with a locked palette.winterize.py,burnify.pyandsideon.pyredraw an existing sprite under snow, on fire, or seen end-on.icons.pydraws the UI icons as pixel grids and emits them as SVG. These need aGEMINI_API_KEYin a.envat the repo root, which is not in the repository and should not be. - Saves live in
localStorage, which browsers delete. The game can write a colony out to a file and read it back; that is the only copy a browser cannot throw away.
v0.9 — beta. Feature-complete and stable; what it wants now is other people playing it. The in-game update log (WHAT HAS CHANGED, on the front door) is the running history and is kept beside the code that it describes.
Faults and thoughts: open an issue on this repository.
All rights reserved — free to play, free to read, not free to republish or sell. See LICENSE; permission is not hard to get, just ask.
Every source file carries the copyright, and the game checks where it is being served from: a copy put up somewhere it does not belong announces itself as one on its own front door, with a link back here. That is a deterrent and not a lock — the whole game is plain source delivered to the browser, so nothing in it can stop a determined person, and the licence is what actually protects it.
Moving the game to a new address? Add the new hostname to
HOME_HOSTSnear the top ofgame.js, or the real site will call itself a copy.