Phaser AE

Track networks

Free packv3.0.0-42D and 3DLogic

A directed graph of curves, written as plain data, with walkers that travel it at an even speed, choose a branch at each junction and know how far they still have to go. It is the route a tower-defence wave follows, a patrol with forks, carts on a rail network or a race circuit's centre line.

This is a Free pack. Every phaser.io account can use it in their games.

Released October 14, 2026 · updated October 19, 2026

Track networks: a screenshot of its demo
A note about these graphics

Expansion packs don't come with graphics. This screenshot is one way of drawing what the pack does, made for its demo: none of the sprites, tiles or backgrounds in it are in the pack.

That's by design. A pack is a game's logic, mechanics and effects, and it works with whatever art you give it. Some packs draw effects, backdrops or 3D scenes of their own, but none carries a game's sprites.

So the look is yours. Make the art on phaser.io, bring your own, or let your agent draw it in code: the same pack can look like anything.

What it does

You describe a network as named nodes and directed edges. An edge with no via is a straight line; otherwise it is a chain of path-notation segments from its start node to its end node: lines, quadratic and cubic curves, arcs, spirals and waves. A node with no outgoing edges is a goal, and one with no incoming edges a spawn, unless you name them yourself. new Track bakes the whole network once into arc-length tables, so walkers keep an even speed round the tightest curve.

track.spawn(speed) puts a walker on the network. Each step advance(dt) moves it by arc length, carrying it across junctions, and you read its x, y and angle for the sprite. At a junction the walker asks its chooser first, if it has one, and otherwise draws a branch weighted by each edge's weight, which you can change live to bias a junction. distanceToGoal is the distance left along the track to the nearest goal, so finding the walker closest to the exit is one comparison.

Everything is deterministic. Unnamed spawns and weighted branches draw from the walker's stream or the track's, and a fork of the game's stream makes the game's seed decide every route. A walker's state snapshots as JSON-safe data. distanceToTrack measures how far a point is from any edge, which keeps a tower from being built on the road.

Features

  • Nodes and directed edges — a network in plain data, with spawns and goals found for you or named.
  • Curved edges — lines, quadratic and cubic curves, arcs, spirals and waves in path notation.
  • Even speed — walkers move by arc length, with a live speed to slow or boost them.
  • Branching by weight or policy — weighted draws you can change live, or a chooser for a points switch, a player's choice or a shortest-route rule.
  • Distance to goal — for turrets that aim at the leader and for progress bars.
  • Staggered starts — startDist starts a walker part-way along, spacing out a wave.
  • Placement checks — distanceToTrack keeps buildings off the route.
  • Transforms at bake — flipX, flipY and offset mirror and move a whole layout.
  • Ready to draw — each edge carries a polyline sampled about every 8 units.
  • Seeded and saveable — branch streams from a seed, and walker snapshots as JSON.

Good for

  • Tower defence, with paths that fork and rejoin and towers that target the leader.
  • Patrol routes with forks in a stealth or strategy game.
  • Trains and carts on rails, with points the player switches.
  • Top-down race circuits, as the centre line racers follow.
  • Conveyors and fairground rides that follow a fixed path through a level.
  • 3D games on the ground plane, reading the walker's y as Z.

Make it yours

The network is data, and the walkers take options: from a named spawn, their own rng, a startDist and a choose policy. The track takes flipX, flipY, offset, samplesPerSegment (48 by default, at least 8) and a default rng.

Two different uses: a tower-defence map whose path forks round a lake, with three in four walkers taking the top branch, towers aiming at the walker with the lowest distanceToGoal, and distanceToTrack refusing tower spots too close to the road; and a train set where a chooser reads a points switch the player flips, on a loop with no goal so the trains run for ever.

A quick look

A fork weighted three to one, and a walker moving a sprite:

import { Track } from '@phaser-ae/track';
const track = new Track({
    nodes: { in: [0, 300], fork: [400, 300], top: [800, 120], bot: [800, 480], out: [1200, 300] },
    edges: [
        { from: 'in', to: 'fork' },
        { from: 'fork', to: 'top', via: [{ quad: [[600, 120], [800, 120]] }], weight: 3 },
        { from: 'fork', to: 'bot', via: [{ quad: [[600, 480], [800, 480]] }] },
        { from: 'top', to: 'out' }, { from: 'bot', to: 'out' },
    ],
}, { rng: game.rng.fork('track') });
const w = track.spawn(140, { startDist: 30 });
game.step('wave', dt => { if (w.advance(dt)) leak(); sprite.x = w.x; sprite.y = w.y; sprite.rotation = w.angle; });

Works with

  • path-notation — the curve notation its edges are written in.
  • track-racer — top-down circuit racing built on it.
  • steering — free movement and flocking, rather than fixed routes.
  • nav — flow fields for movement across open ground.
  • pseudo-road and road-data — pseudo-3D racing roads with splits and merges.
  • rail-route — on-rails camera routes through 3D legs and branches.
  • rail — a chain of balls pushed along one path.

Good to know

  • The graph is fixed once built, and only weights change: build a new Track for a new layout.
  • Edges are one-way; a two-way road is two edges.
  • distanceToTrack scans every edge: fine for placement checks, not a per-frame query for hundreds of objects.
  • A walker stops at a goal, and a loop is a graph with no goal.
  • There are no events and no collisions between walkers: read done, edge and distanceToGoal after advance, and space walkers out with startDist.

More Logic packs

Show all →