Building a Region
A region is a field of pointy-top hexagons in axial coordinates. This chapter is how to make another one.
Axial coordinates, and why
Every tile carries q and r. The six neighbours are six constant offsets, identical for every tile on the board:
| Direction | q | r |
|---|---|---|
| east | +1 | 0 |
| west | −1 | 0 |
| northeast | +1 | −1 |
| northwest | 0 | −1 |
| southeast | 0 | +1 |
| southwest | −1 | +1 |
The obvious alternative — offset rows, numbered like a grid — needs a different rule for odd and even rows. Axial does not. That matters more here than in ordinary software, because the GM computes neighbours in its head on every single move, and a parity branch is a thing a language model gets wrong at 3am in the middle of a session.
The same choice pays off again in the token expressions, which come out as one line instead of a conditional.
Nothing records connections
There is no adjacency list, no exits array, no door table. Two tiles are connected because their coordinates differ by one of those six offsets. Connectivity is arithmetic.
This is the deep difference from the dungeon floors this system replaced, where the layout was a graph somebody drew by hand. Here you place ground, and the graph falls out.
Start from the generator
Do not hand-write coordinates. hexfield.js emits the geometry block, the tiles array and the map polygons for a hex-shaped field of any radius:
node hexfield.js --radius 2 --aspect 4:3 --out field.json
Radius 1 gives 7 tiles, 2 gives 19, 3 gives 37. Radius 2 on a 4:3 canvas lands on clean numbers and produces a 3-4-5-4-3 board.
Then assign terrain, creatures and discoveries to the tiles it gave you, set entryTileId and currentTileId, and check it.
Shape the region with ground
Routing comes from terrain, and the interesting part of a region is where impassable ground forces a detour. In @Missing file, open water cuts the eastern marsh off from the west so completely that it touches the walkable region at one edge — reaching it means going the long way round the south.
That detour is the region's best feature and it is authored entirely in terrain. No doors, no locks, no scripting.
Aim for one or two of those. A board with no constraint is a field; a board that is all constraint is a corridor with extra steps.
Always check reachability
node check-region.js "Regions/Your Region.region.json"
It catches duplicate coordinates, references that resolve to nothing, barriers naming non-directions, tiles falling off the canvas, and — the important one — any passable tile with no route from the entry.
Leave the entry empty
The tile the traveller starts on should hold nothing. A player attacked before their first decision has not been given a game yet.