# Example games

> The eleven example games in templates/crescent-game/examples, what each one shows, which engine pieces or module it uses, which files to read first, and how to run one.

The template ships eleven complete games in `templates/crescent-game/examples/`. Each is one self-contained `index.tsx` that default-exports a `GameDefinition`, so any of them can replace the game in `src/game/index.tsx`. Use them two ways: to see how an engine piece or module is used in a real game, and as the starting point for your own game of that kind.

The twelfth game is the starter, **Sunset Sprint**, in `src/game/index.tsx`: a [racing module](https://docs.moonspell.app/modules/racing.md) config.

## At a glance

| Example | Kind of game | Built on | 2D or 3D |
| --- | --- | --- | --- |
| [moon-blocks](https://docs.moonspell.app/examples.md#moon-blocks) | block puzzle, endless | [puzzle module](https://docs.moonspell.app/modules/puzzle.md), `block` pack | 2D |
| [moonrise](https://docs.moonspell.app/examples.md#moonrise) | merge puzzle with levels | puzzle module, `merge` pack, drawn tiles | 2D |
| [gem-cascade](https://docs.moonspell.app/examples.md#gem-cascade) | match-three with levels | puzzle module, `match` pack in swap mode | 2D |
| [flag-rush](https://docs.moonspell.app/examples.md#flag-rush) | 3 v 3 capture the flag | [shooter module](https://docs.moonspell.app/modules/shooter.md) | 3D |
| [oath-of-ashvale](https://docs.moonspell.app/examples.md#oath-of-ashvale) | story-led town builder with sorties | [kingdom module](https://docs.moonspell.app/modules/kingdom.md) | 3D |
| [rooftop-hop](https://docs.moonspell.app/examples.md#rooftop-hop) | parkour course over a void | [character and cameras](https://docs.moonspell.app/engine/character-and-cameras.md) | 3D |
| [lantern-tag](https://docs.moonspell.app/examples.md#lantern-tag) | collect lanterns, avoid guards | [bots](https://docs.moonspell.app/engine/bots.md) | 3D |
| [pulse-arena](https://docs.moonspell.app/examples.md#pulse-arena) | free-for-all against armed bots | [combat](https://docs.moonspell.app/engine/combat.md) | 3D |
| [tap-pop](https://docs.moonspell.app/examples.md#tap-pop) | one-tap arcade, 30 second rounds | [2D layer](https://docs.moonspell.app/engine/2d.md) | 2D |
| [sky-runner](https://docs.moonspell.app/examples.md#sky-runner) | side-scrolling platformer | 2D layer platformer kit | 2D |
| [moon-chess](https://docs.moonspell.app/examples.md#moon-chess) | chess against talking rivals or a friend | [turns](https://docs.moonspell.app/engine/turns.md) | 2D |

The five module examples are configs: change fields, not code. The six others write their own loop on the engine pieces, so everything (level, rules, camera, HUD) is in that one file.

## How to run an example

An example runs by becoming the game. From `templates/crescent-game`:

```bash
cp examples/lantern-tag/index.tsx src/game/index.tsx
npm run typecheck
```

Then start the game the way the Quickstart describes, for example in a browser with `npm run web`. To go back to the starter game, restore the file with `git checkout src/game/index.tsx`.

Run instructions: see [Quickstart](https://docs.moonspell.app/start/quickstart.md).

The relative `require('../../assets/...')` paths in the examples resolve the same from `examples/<name>/` and from `src/game/`, so the copy needs no edits. Every example is checked by `npm run typecheck`, because the template's TypeScript config includes `examples/`.

All examples keep the same dev conventions: in development builds they show a `hud-debug` telemetry line and an **AUTO** button that plays the game by itself, every control has a `testID`, and the exit control calls `onExit`. Production builds hide the dev pieces.

Examples with a leaderboard or rooms work without a backend: scores stay on the device and rooms hold only you. To put them online, set `GAME_BACKEND_URL` and deploy the backend scaffold ([backend overview](https://docs.moonspell.app/backend/overview.md)); each leaderboard name an example uses must be in the backend's `BOARDS`.

## Module examples

### moon-blocks

**Moon Blocks**: the puzzle module's starter. The `block` pack, endless, on a night-sky palette. Drag pieces from the tray onto the 8 x 8 board; full rows and columns clear; the round ends when no piece fits.

- Shows: the smallest real puzzle config: `pack`, `mode`, `board`, `block.pieces`, `block.tray`, `theme` colours and `tileStyle`.
- Read first: `examples/moon-blocks/index.tsx` (30 lines), then [Puzzle module](https://docs.moonspell.app/modules/puzzle.md).
- Backend: the module's `endless` board and presence, already in the scaffold's `BOARDS`.

### moonrise

**Moonrise**: a merge puzzle in the night sky. Swipe to slide; two equal bodies become the next one, from a new moon through full moons, planets, a sun and a galaxy to the last step. Levels ask for the next body each time.

- Shows: the `merge` pack in `levels` mode, `theme.names` naming every step, every tile drawn in code with `theme.paintTile`, a twinkling starfield with `theme.paintBackground`, and a font family picked with `fonts`.
- Read first: `examples/moonrise/index.tsx`: the `paintTile` switch is the part to study for drawing tiles with the 2D layer's `Draw2D`.
- Backend: the module's `levels` board.

### gem-cascade

**Gem Cascade**: a match-three. Drag a gem onto a neighbour to line up three or more; lines shatter, gems fall, and new lines clear on their own as cascades. Levels ask for a number of gems in a few moves.

- Shows: the `match` pack with `input: 'swap'`, levels, six gem cuts drawn with `paintTile` (one shape per colour, so colours also read by shape), `draw.clip` for facets, drifting sparkles in `paintBackground`, a custom `hint`.
- Read first: `examples/gem-cascade/index.tsx`.

### flag-rush

**Flag Rush**: three against three capture the flag on the `depot` map, first to three captures. Bots fill every empty seat; friends who join take a bot's place in the same match.

- Shows: a full shooter config: `mode: 'ctf'`, `rules`, `map`, `player` loadout and camera, team names and colours, `seats`, bot difficulty and weapons, `pickups`.
- Read first: `examples/flag-rush/index.tsx` (27 lines), then [Shooter module](https://docs.moonspell.app/modules/shooter.md). Change `mode` for team deathmatch, gun game, king of the hill or free-for-all.
- Backend: rooms from the scaffold as shipped; add `flag-rush-kills` to `BOARDS` for the kills leaderboard.

### oath-of-ashvale

**Oath of Ashvale**: a storybook realm with a queen, a marshal and a farmer. Two chapters of dialogue with cut-out portraits, a knight-or-ranger choice, joystick sorties against bandit camps in the fog, Victory rewards, wheat and carrots, a watchtower, a barracks and land to clear.

- Shows: every table of the kingdom config filled in: resources with sheet icons, eight buildings with generated `.glb` models, crops, units and classes on rigged character models with shared animation files, `held` weapons, `tint` per team, two missions, a town with prebuilt buildings, plots, debris, paths, a water row and walking villagers, a story of two chapters (16 and 13 beats), a full `sounds` set and the `kingdom-power` board.
- Read first: `examples/oath-of-ashvale/index.tsx`: the `story` block shows the beat order that works (title, say, class choice, sortie, objectives, reward, unlock).
- Assets: the characters and weapons are the KayKit Adventurers pack (by Kay Lousberg, CC0) in `assets/models/kaykit/`; the buildings in `assets/models/ashvale/`; the portrait and icon sheet in `assets/sprites/oath-of-ashvale/sheet.png`; music and effects in `assets/audio/ashvale/` and `assets/sfx/ashvale/`.
- Backend: add `kingdom-power` to `BOARDS` for the leaderboard; the save syncs through `PlayerSaves`.

## Engine-piece examples

### rooftop-hop

**Rooftop Hop**: a parkour course over a void. Move with the left stick, drag the right half to look, JUMP across gaps. Rings are checkpoints, the green pad is the goal, falling returns you to the last checkpoint. The camera button cycles third person, first person, top-down and side view.

- Shows: the character controller (`createCharacterState`, `stepCharacter`, `resolveCharacterParams`), the four camera rigs (`resolveCameraRig`, `CharacterCamera`, `nextCameraMode`), `CharacterControls`, a level from `resolveLevel` drawn with `LevelMeshes`, a moving platform on a path (`createPath`, `MovingPlatform`), checkpoints and the goal as zones (`useZones`), game feel (`GameFeel`, `juice`, `stretch`), a waypoint autopilot (`createWalker`, `waypointCommand`) and a fastest-time leaderboard.
- Read first: `examples/rooftop-hop/index.tsx`, then [Character and cameras](https://docs.moonspell.app/engine/character-and-cameras.md).
- Backend: board `rooftop-hop`, lowest first.

### lantern-tag

**Lantern Tag**: collect five lanterns in an arena while three guards patrol. They hear you sprint and land, see you when you cross their view, chase you and lose you again. Three lives.

- Shows: bots (`BotSquad`, `BotMeshes`, `createRoster`, patrol routes, hearing and sight, `backOff`), pathfinding on a grid (`gridMap`, `findPath`, `nearestWalkable`), a hut and ramps laid out from a text map, a slow title orbit (`CameraDolly` on a closed path), typed signals between systems (`createSignals`, `useSignal`), positional sound (`useAudioMixer`, `AudioListener`), particles and a leaderboard.
- Read first: `examples/lantern-tag/index.tsx`, then [Bots](https://docs.moonspell.app/engine/bots.md) and [Audio](https://docs.moonspell.app/engine/audio.md).
- Backend: board `lantern-tag`, lowest first.

### pulse-arena

**Pulse Arena**: free-for-all in a neon arena against three armed bots, first to ten eliminations. Hold FIRE to shoot (the same thumb aims), SWAP cycles rifle, shotgun and rockets, aim assist pulls the crosshair onto enemies, everyone respawns.

- Shows: the combat kit with no module around it: `CombatWorld`, weapons (`spreadOf`, `isReloading`), bot gunners (`createGunner`, `driveBotWeapon`), `CombatEffects`, and the combat HUD (`Crosshair`, `HitMarker`, `HealthBar`, `AmmoCounter`, `DamageNumbers`, `Killfeed`).
- Read first: `examples/pulse-arena/index.tsx`, then [Combat](https://docs.moonspell.app/engine/combat.md). Start here for a shooter rule the shooter module has no mode for (waves, bomb defusal).
- Backend: board `pulse-arena`, lowest first.

### tap-pop

**Tap Pop**: dots drift around the screen; tap one to pop it before the 30-second timer runs out, with a local best.

- Shows: the 2D layer end to end: `GameCanvas2D`, stage units that fit any phone, taps mapped to the stage (`PointerEvent`), the fixed-step loop, tweens (`createTweens`), particles (`createParticles2D`), text, `haptics`, a one-shot sound (`useOneShots`), a seeded random (`makeRng`), a font family from `@/engine/ui/fonts`, and the HUD chrome (`TopBar`, `Banner`, `FinishCard`, `RoundButton`). It also has a dev performance scene (64 tiles and 200 particles).
- Read first: `examples/tap-pop/index.tsx`, then [2D layer](https://docs.moonspell.app/engine/2d.md). Start here for any flat game: one-tap arcade, cards, word games.
- Backend: board `tap-pop`, highest first.

### sky-runner

**Sky Runner**: a side-scrolling run across rooftops drawn from a tile map: coins, spikes that send you back, one-way ledges, a flag at the end.

- Shows: the 2D platformer kit: a tile map from strings (`createTileMap`, `drawTileMap`), the platformer controller (`createPlatformer`, `stepPlatformer`, `platformerInput`: coyote time, jump buffer, short hops, wall slides and wall jumps), triggers (`Triggers2D`), a follow camera (`createCamera2D`, `cameraView`), two parallax layers (`drawParallax`), sprite sheets drawn in pixel-art mode (`createSheet`, `createSpriteAnimator`, `pixelZoom`) with vector shapes as the fallback, and an autopilot built on `raycast2D`.
- Read first: `examples/sky-runner/index.tsx`: the `MAP` strings and the `autopilot` function.
- Assets: `assets/sprites/sky-runner/runner.png` and `roof-tiles.png`.

### moon-chess

**Moon Chess**: chess on the 2D layer against three computer rivals at easy, medium and hard who talk, against a friend online, or pass-and-play on one phone. A drawn board and pieces, tap or drag to move, slides, a promotion picker, take-backs.

- Shows: the turns kit: `chessRules` and the chess helpers (`createChess`, `playMove`, `legalMovesFrom`, `san`, `toFen`, `undoMove`), the search (`searchMoves`, `pickMove`), the computer opponent (`useOpponent`), online turns (`useTurnRoom`: seats, resign, rematch with colours swapped), room codes and launch links (`makeRoomCode`, `useLaunchRoomId`, `roomInviteUrl`), presence and a leaderboard.
- Read first: `examples/moon-chess/index.tsx` (the largest example, about 1300 lines), then [Turns](https://docs.moonspell.app/engine/turns.md). For another board game, keep its screens and flow and swap `chessRules` for your own `TurnRules`.
- Backend: the rivals' lines come from the backend's model (`POST /ai/turn`, see [AI opponent](https://docs.moonspell.app/backend/ai-opponent.md)); offline the search still plays, silently. Online games need rooms.

## Picking a starting point

| You want | Copy |
| --- | --- |
| a block, merge, match or sort puzzle | moon-blocks, moonrise or gem-cascade, then change the config |
| a shooter with standard modes | flag-rush |
| a town builder with a story | oath-of-ashvale |
| a 3D platformer or obstacle course | rooftop-hop |
| tag, stealth, chase, enemies that patrol | lantern-tag |
| a shooter with your own rules | pulse-arena |
| any flat arcade, card or word game | tap-pop |
| a 2D platformer or runner | sky-runner |
| a board game | moon-chess |
| a car race | the starter game in `src/game/index.tsx` |
