The pack
wireCockpit
function wireCockpit(): Pack<{ wireCockpit: typeof api }>
Install the wire cockpit API.
Helpers
ATARI
const ATARI: { readonly red: "#ff2020"; readonly green: "#20ff40"; readonly blue: "#3050ff"; readonly yellow: "#ffff30"; readonly cyan: "#30ffff"; readonly magenta: "#ff30ff"; readonly white: "#ffffff"; }
The seven pure colours of the Atari colour X-Y monitor.
bandCentres
function bandCentres(depth: number): number[]
Band centre heights (top first) for a trench depth deep.
cockpitScene
function cockpitScene(c: Cockpit, o: SceneOptions): SceneLine[]
Build the scene for the current phase.
createCockpit
function createCockpit(def: CockpitDef): Cockpit
Validate and build a session.
defaultModels
function defaultModels(): Record<string, ModelPart[] | ((t: RailTarget, time: number) => ModelPart[])>
The built-in models by kind.
difficultyPreset
function difficultyPreset(name: "easy" | "normal" | "arcade"): DifficultyScale
Built-in difficulty presets. arcade is the original tables with the manual's Moderate setting.
empirePreset
function empirePreset(o: EmpireOptions = {}): CockpitDef
The Empire Strikes Back definition.
ESB_CHOICES
const ESB_CHOICES: StartChoice[]
The ESB select screen: three planets.
ESB_QUOTAS
const ESB_QUOTAS: Array<[number, number, number]>
Quotas per wave: probots, walkers, TIEs (waves 1-11; later waves keep the last row).
ESB_SCRIPTS
const ESB_SCRIPTS: Record<string, ShipScript>
ESB TIE choreographies: no Vader; swoops and crossing passes.
esbWaveStages
function esbWaveStages(ctx: WaveContext, o: EmpireOptions = {}): StageDef[]
The stages for one ESB wave.
registerStage
function registerStage(type: string, m: StageModule): void
Register a built-in stage type (used by this pack's stage modules).
splitSteps
function splitSteps(): ShipStep[]
The cabinet's SPLIT prefix: settle, then a random four-way break (up/down, straight/rolling) at 768 per frame.
starWarsPreset
function starWarsPreset(o: StarWarsOptions = {}): CockpitDef
The Star Wars definition: select screen, waves, shields, tally.
surfaceSpeed
function surfaceSpeed(st: Pick<SurfaceStage, "speed">, s: number): number
Forward speed per frame at distance s on a surface run (the cabinet's +1 per frame ramp).
SW_CAMERA
const SW_CAMERA: CameraDef
The cabinet's camera: a 90-degree horizontal view on a 4:3 screen; the cursor reaches 7/8 of the way out.
SW_CHOICES
const SW_CHOICES: StartChoice[]
The select screen: three Death Stars, placed where the cabinet's screen shows them (left, bottom centre, right).
SW_DOGFIGHT_FIRE
const SW_DOGFIGHT_FIRE: FireRow[]
Dogfight fire table by hardness (the cabinet's TGPROB): window mask, chance per window, guns usable.
SW_FORCE_BONUS
const SW_FORCE_BONUS: number[]
Use-the-Force bonus by displayed wave (5+ pays 100,000).
SW_SCRIPTS
const SW_SCRIPTS: Record<string, ShipScript>
Ship scripts: A straight in and "be mean", B weaving, C weave then climbing passes, D waits then jinks, D3 Vader.
SW_SURFACE_GUNS
const SW_SURFACE_GUNS: number[]
Surface gun slots by hardness (TGNGD).
SW_TOWER_COUNTS
const SW_TOWER_COUNTS: Record<number, number>
Tower and bunker counts per displayed wave 2..11 (waves 12-20 add four towers).
SW_TRENCH_FIRE
const SW_TRENCH_FIRE: TrenchFire[]
Trench wall-gun table by hardness (TGPROB and TGNBS; hardness 0 aims at the sideline).
swCatwalkCells
function swCatwalkCells(wave: number): number
Catwalk cells per trench by displayed wave (wave 1 has none; 82 on wave 2, 140 on wave 4, about 220 from 8).
swShipQueue
function swShipQueue(wave: number): { queue: ShipSpawn[]; repeatFrom: number }
The ship queue for a displayed wave and the index its endless tail starts at (TSPWAV sets A1-A6).
swSurfaceField
function swSurfaceField(pattern: (typeof PATTERNS)[number], towers: number, extra = 0, seed = 1): SurfaceObject[]
Build a surface field: towers towers among 28 (or 32) entries on the cabinet's 4096 grid, in a named arrangement.
swSurfaceForWave
function swSurfaceForWave(wave: number, seed: number): SurfaceObject[]
The field for a displayed wave (2 is bunkers only; 21+ picks one of the last six at random).
swTrench
function swTrench(wave: number, slots: number, seed: number): TrenchSlot[]
Generate a trench of slots slots: an open intro, catwalk rows (singles, doubles, triples and halves that
always leave a way through), wall guns and panels, and a clear run to the port.
swWaveStages
function swWaveStages(ctx: WaveContext, o: StarWarsOptions = {}): StageDef[]
The Star Wars stages for one wave.
Functions
asteroid
function asteroid(r: number, seed: number): WireModel
A faceted asteroid of radius r (deterministic from seed).
atAt
function atAt(phase = 0): ModelPart[]
ESB AT-AT walker (about 2600 tall, facing +z): body, neck, head with a red eye, four jointed legs.
atSt
function atSt(phase = 0): ModelPart[]
ESB AT-ST scout walker (about 1500 tall).
box
function box(min: Vec3, max: Vec3): WireModel
A box outline from two corners.
deathStar
function deathStar(r: number): ModelPart[]
The Death Star seen from space: a disc outline, its dish and equator (radius r, facing -z toward the viewer).
frustum
function frustum(y0: number, hx0: number, hz0: number, y1: number, hx1: number, hz1: number): WireModel
A frustum between two horizontal rectangles (half-sizes) at two heights.
line
function line(points: Vec3[]): WireModel
An open polyline.
loop
function loop(points: Vec3[]): WireModel
A closed loop through points.
mergeModels
function mergeModels(list: WireModel[]): WireModel
Merge several models into one.
ring
function ring(r: number, n: number, plane: "xy" | "yz" | "xz", c: Vec3 = { x: 0, y: 0, z: 0 }, phase = 0): WireModel
A ring of n points of radius r in a plane: 'xy' faces forward, 'yz' faces sideways, 'xz' lies flat.
sparkler
function sparkler(r: number, arms: number, spin: number): WireModel
A fireball sparkler as a model facing the viewer: arms spokes of radius r with crossbars at the tips.
trenchStatus
function trenchStatus(c: { state: { stageData: Record<string, unknown> } }, key: string): { portHit: boolean; torpedo: number; pass: number; portPlaced: boolean } | null
The trench's per-stage state the scene reads (port, torpedo, Force, pass).
Constants
BUNKER
const BUNKER: WireModel
A bunker: a red truncated pyramid 1440 tall.
CATWALK
const CATWALK: WireModel
A catwalk (force field) in wall-local axes: three bars running 640 out from the wall at the band.
PANEL
const PANEL: WireModel
A decorative trench wall panel: outer 512 deep by 384 tall, inner 256 by 128.
PORT_BASE
const PORT_BASE: WireModel
The exhaust port parts, lying on the floor: base, berm and hole.
PORT_BERM
const PORT_BERM: WireModel
The port's turquoise berm.
PORT_HOLE
const PORT_HOLE: WireModel
The port's red hole.
PROBOT
const PROBOT: ModelPart[]
ESB probe droid: a domed head on dangling legs (about 900 tall).
TIE
const TIE: WireModel
Star Wars TIE fighter (wings span 416, 468 tall; arcade model scale 13).
TOWER_BODY
const TOWER_BODY: WireModel
A Star Wars laser tower: tapering yellow column, white hat from 12480 to 13920.
TOWER_HAT
const TOWER_HAT: WireModel
The tower's hat (the shootable top).
TOWER_STUB
const TOWER_STUB: WireModel
The stub cap shown once the hat is shot off.
TURRET
const TURRET: WireModel
A trench wall turret in wall-local axes (x into the trench, y up, z along it): plate, body and muzzle.
VADER_TIE
const VADER_TIE: WireModel
Darth Vader's TIE Advanced: bent wings, a longer body (wings 540 wide, 360 long, 260 tall).
Types
ApproachStage
interface ApproachStage extends StageDef
The approach stage: a timed hold while the Death Star grows (the cabinet's 57 frames).
type: "approach"— Stage type idapproach.duration: number— Seconds.
AsteroidStage
interface AsteroidStage extends StageDef
The asteroid field: survive to the far side; asteroids cost shields; TIEs keep attacking.
type: "asteroids"— Stage type idasteroids.length: number— Field length.density: number— Asteroids per 10,000 units.spread: [number, number]— Field half-width and half-height.tieEvery: number— Seconds between TIE passes.letter: string— Letter earned by crossing without losing a shield.letterPoints: number— Letter points.points: { tie: number; shot: number; asteroid: number }— Points: TIE, shot, asteroid.flight: { speed: number; rates: [number, number] }— Flight.
Banner
interface Banner
A HUD line the arcade shows.
text: string— Text.color: string— CSS colour.row: number— Row: 0 is under the shield gauge, higher rows lower.size?: number— Relative size (1 normal, 2 double).flash?: boolean— Flashing.
Cockpit
interface Cockpit
A running game.
readonly def: CockpitDef— The definition.readonly state: CockpitState— State.readonly rail: Rail— The current wave's rail (a select-screen rail before play).readonly wave: WaveDef— The current wave definition.readonly stage: StageDef | null— The current stage definition.attract(): void— Show the attract screen.begin(): void— Coin up: the select screen (or straight in without choices).start(wave?: number, bonus?: number): void— Start at a wave directly, with the start bonus for it.tick(seconds: number, input?: CockpitInput): void— Advance by seconds.step(input?: CockpitInput): void— One fixed step.drain(): CockpitEvent[]— Take events.setDifficulty(d: DifficultyScale): void— Set the difficulty (applies from the next wave).snapshot(): { state: CockpitState; rail: ReturnType<Rail["snapshot"]> }— Snapshot (session and rail).restore(s: { state: CockpitState; rail: ReturnType<Rail["snapshot"]> }): void— Restore a snapshot into a session built from the same definition.
CockpitDef
interface CockpitDef
The full game definition.
title?: string— Game name.waves: (ctx: WaveContext) => WaveDef— Build a wave.choices?: StartChoice[]— Start choices; empty starts atstartWavewith no select screen.startWave?: number— Wave a game starts at when there are no choices (default 1).shields: number— Starting shields.bonusShields?: number— Shields added after each completed wave (capped atshieldCap).shieldCap?: number— Shield cap (defaultshields).invulnerable?: (shieldsBefore: number) => number— Seconds of immunity after a shield is lost, from the count before the hit.difficulty?: DifficultyScale— Difficulty.tally?: TallyDef— End-of-wave tally.timing?: Partial<CockpitTiming>— Timings.camera?: CameraDef— Camera (field of view, crosshair limits).riderRadius?: number— Rider collision radius.gun?: { duration?: number; cooldown?: number }— Gun (default the Star Wars beam: 8 frames, follows the cursor, one press per shot).stageTypes?: Record<string, StageModule>— Extra stage types.seed?: number— Seed.step?: number— Fixed step (default 1/60).hiScore?: number— Initial high score.maxWave?: number— Highest wave; the counter stops there (Star Wars: 99).choiceArt?: "death-star" | "planet"— Art for the start choices: Star Wars' Death Stars or ESB's striped planets.letters?: { word: string; points: number; force: number }— Letters spelled across stages (ESB: JEDI pays 20,000 and grants the Force for a while).
CockpitEvent
type CockpitEvent = | { type: "phase"; phase: CockpitPhase } | { type: "wave-start"; wave: number; hardness: number } | { type: "stage-start"; stage: string; index: number } | { type: "score"; points: number; reason: string; at?: Vec3 } | { type: "explode"; what: string; at: Vec3; big?: boolean } | { type: "laser"; aim: { u: number; v: number }; left: boolean } | { type: "fireball"; kind: string; at: Vec3 } | { type: "shot-down"; kind: string; at: Vec3 } | { type: "shield-hit"; shields: number; cause: string } | { type: "speech"; line: string } | { type: "message"; text: string } | { type: "tally"; text: string; points: number } | { type: "wave-complete"; wave: number } | { type: "game-over"; score: number }
Events for presenters and sound.
CockpitInput
interface CockpitInput
Input each step.
aim?: { u: number; v: number }— Crosshair as a view-plane aim(u, v).fire?: boolean— Lasers (trigger held).secondary?: boolean— Secondary weapon (ESB tow cable; thumb buttons).
CockpitPhase
type CockpitPhase = "attract" | "select" | "play" | "dying" | "explosion" | "tally" | "over"
Session phases.
CockpitState
interface CockpitState
Plain-data session state.
phase: CockpitPhase— Phase.phaseTime: number— Seconds in the phase.wave: number— Displayed wave.startWave: number— Wave the game started at.startBonus: number— Start bonus still owed.completed: number— Waves completed this game.dif: number— Difficulty step (GM.DIF).bump: number— Difficulty bump (GM.BMP).hardness: number— Hardness index this wave.score: number— Score.hiScore: number— High score.last: { points: number; age: number }— Last points added and seconds since.shields: number— Shields (mirrors the rail).stage: number— Stage index in the wave.stageType: string— Stage type.select: { left: number; hover: number }— Select screen.tally: { lines: Banner[]; next: number; items: Array<{ text: string; points: number; shields?: number }> }— Tally lines shown so far.banners: Banner[]— HUD banners this step.stageData: Record<string, unknown>— Per-stage module state (plain data, keyed by stage type).counters: Record<string, number>— Per-wave counters modules share (towers left, letters, quotas).steps: number— Fixed steps so far.rng: number[]— The seeded random stream's state: four words, from the kernel'srng.snapshot(). It advances in place and is saved with the state.firstWave: boolean— Whether the current wave is the first of the game.roll: number— View roll applied by death and hits outside the rail (radians).letters: string— Letters earned towarddef.letters.word.force: number— Seconds of the Force (invulnerability) left.
CockpitTiming
interface CockpitTiming
Fixed timings in seconds.
select: number— Select screen countdown.dying: number— Death: the growing GAME OVER.explosion: number— End-of-wave explosion (0 skips it).over: number— Game over screen before attract.
DifficultyScale
interface DifficultyScale
Easy / Normal / Arcade scaling. Arcade is the cabinet with the manual's recommended switch settings.
name: string— Preset name.dif: number— Starting difficulty step (the cabinet's GM.DIF: Easy 0, Moderate 1, Hard 2, Hardest 3).bumpCap: number— Most the per-wave difficulty bump may grow to (the cabinet: 4).hardCap: number— Highest hardness index used (the cabinet: 15).fire: number— Enemy fire chance multiplier (1 = the cabinet).projectile: number— Enemy projectile speed multiplier (1 = the cabinet).
DogfightStage
interface DogfightStage extends StageDef
The dogfight stage definition.
type: "dogfight"— Stage type iddogfight.duration: number— Seconds before the retreat (Star Wars: 21, or 19.05 on a game's first wave). 0 = no timer.quota?: number— End when this many ships are destroyed (ESB's TIE stage), 0 = never.slots: number— Simultaneous ships (3).queue: ShipSpawn[]— Ship queue; ships afterrepeatFromcycle forever.repeatFrom: number— Queue index the cycle restarts at.scripts: Record<string, ShipScript>— Choreographies by id.fire: FireRow— Fire table row for this wave.frameRate: number— Game frame rate the per-frame numbers use (20).speedScale?: number— Ship speed scale on per-frame speeds (1).points: Record<string, number>— Points per kind destroyed.hitPoints?: Record<string, number>— Points per hit on an indestructible kind (Vader: 2,000).fireballPoints: number— Fireball points (33).spin?: number— Seconds a hit indestructible ship spins away (31 frames).startYaw?: number— Starting view yaw (pi: facing away, so the view swings round).hints?: Banner[]— Banners for the first wave of a game (alternating every 16 frames for 5 seconds).deathStar?: number— The Death Star's distance ahead for the presenter (0 = none).fireball?: string— Fireball kind id (default'fireball').
EmpireOptions
interface EmpireOptions
Options for the Empire Strikes Back definition.
shields?: number— Starting shields (2-5; default 4).difficulty?: DifficultyScale— Difficulty (default normal).quotaScale?: number— Quota scale (1 = the cabinet's table).extraWalkers?: number— Walkers in the walker stage beyond the quota.cables?: number— Tow cables (4).tieSeconds?: number— TIE stage seconds (an estimate: 30).fieldLength?: number— Asteroid field length (units).density?: number— Asteroids per 10,000 units.seed?: number— Seed.choices?: StartChoice[]— Start choices.
FireRow
interface FireRow
Fire window row: every mask + 1 frames each eligible ship fires with chance, using at most guns slots.
mask: number— Window period minus one (frames).chance: number— Probability a ship fires in a window.guns: number— Fireballs in flight at once.
ModelPart
interface ModelPart
One coloured part of a model; part names the hit region it belongs to (a tower's hat), if any.
color: string— CSS colour.model: WireModel— Points and edges.part?: string— Region id: the part is hidden once that region is destroyed.whenDestroyed?: string— Draw only when this region is destroyed (a tower stub's cap).bright?: number— Brightness multiplier (default 1).
ProbotStage
interface ProbotStage extends StageDef
Hoth: probots hover over the snow and send transmissions; the stage ends when enough get through.
type: "probots"— Stage type idprobots.slots: number— Probots in the air at once.transmissions: number— Transmissions that end the stage (4).sendEvery: number— Seconds between a probot's transmissions.fireEvery: number— Seconds between a probot's shots.points: { probot: number; transmission: number; shot: number }— Points: probot, transmission, shot.flight: { speed: number; altitude: [number, number]; rates: [number, number] }— Flight: forward speed (units/s), altitude range, yoke rates.limit: number— Longest the stage runs (seconds; an estimate).
SceneLine
interface SceneLine
One projected segment in screen units (y down).
x1: number— Start x.y1: number— Start y.x2: number— End x.y2: number— End y.color: string— CSS colour.alpha: number— Brightness 0..1 (depth cue).width: number— Width multiplier (1 normal; dots are 0-length segments).
SceneOptions
interface SceneOptions
Scene options.
w: number— Screen width.h: number— Screen height.oy?: number— The optical centre's offset below the screen centre (the cabinet's VGOFFY), in screen units.time: number— Seconds, for animation.models?: Record<string, ModelPart[] | ((t: RailTarget, time: number) => ModelPart[])>— Models by target kind (defaults to the built-in Star Wars / ESB models).
ShipOp
interface ShipOp
One choreography step: hold these motions for frames game frames.
frames: number— Game frames (at the stage's frame rate).speed?: number— Forward speed, units per frame.up?: number— Speed along the ship's own up axis, units per frame (negative is down).yaw?: number— Turn about the ship's own up axis: -1 left, 1 right.pitch?: number— Turn about its right axis: 1 nose up.roll?: number— Roll about its forward axis.aim?: boolean— Turn toward the player (yaw and pitch toward the player's side).front?: boolean— Turn toward a point 4096 in front of the player; no firing.until?: "fired" | "near" | "sights" | "hit"— End the step early when: it fired, the player is near (4096), the player is in its sights, or it was hit.
ShipScript
interface ShipScript
A ship's choreography: the intro once, then the loop forever.
intro: ShipStep[]— Opening steps.loop: ShipStep[]— Repeating steps.
ShipSpawn
interface ShipSpawn
One ship in the spawn queue.
kind: string— Kind id:'tie'or'vader'(or a custom kind built by the stage).script: string— Script id.at: Vec3— Spawn point in the player's frame: x right, y up, z forward.split?: boolean— Prefix the random split manoeuvre (the cabinet's 2x scripts).
ShipStep
type ShipStep = ShipOp | { pick: ShipOp[][] }
A choreography step or a random choice between sequences.
StageBuild
interface StageBuild
What a module builds into the wave's rail.
legs: LegDef[]— Legs, in route order. Their ids must be unique in the wave.kinds?: TargetKind[]— Target kinds (ids unique in the wave).projectiles?: ProjectileKind[]— Projectile kinds.behaviours?: Record<string, Behaviour>— Behaviours.
StageDef
interface StageDef
A stage of a wave: type picks the module; the rest is that module's data.
type: string— Stage type id (a built-in or one registered instageTypes).objective?: StageObjective— Optional kill objective, counted byStageRuntime.kill.[key: string]: unknown— Free data for the module.
StageModule
interface StageModule
A stage type.
build(stage: StageDef, prefix: string, ctx: WaveContext, def: CockpitDef): StageBuild— Build the stage's legs, kinds and behaviours.prefixmakes ids unique in the wave.enter?(c: StageRuntime): void— Called when the rail enters the stage's first leg.before?(c: StageRuntime): void— Before each rail step.after?(c: StageRuntime, events: RailEvent[]): void— After each rail step, with its events.banners?(c: StageRuntime): Banner[]— HUD banners while the stage runs.
StageObjective
interface StageObjective
A stage's kill objective: shoot quota targets for a bonus (ESB: a JEDI letter and ten-times scoring).
quota: number— Kills needed.label: string— What the HUD calls them (PROBOTS, WALKERS, TIES).points?: number— Points when the quota is met.letter?: string— A letter earned (towardletters.word).multiplier?: number— Score multiplier for this stage's kills after the quota (ESB: 10).
StageRuntime
interface StageRuntime
The context a stage module works through.
rail: Rail— The rail.state: CockpitState— Session state.stage: StageDef— This stage's definition.index: number— Stage index.def: CockpitDef— The game definition.difficulty: DifficultyScale— Difficulty.legs: string[]— This stage's leg ids, as built.random(): number— Seeded random in [0, 1).award(points: number, reason: string, at?: Vec3): void— Add points.kill(points: number, reason: string, at?: Vec3): void— Count a kill toward the stage objective and score it (times the stage multiplier once the quota is met).letter(char: string, points: number): void— Earn a letter now (ESB's asteroid letter is earned by surviving).emit(e: CockpitEvent): void— Emit an event.finish(): void— The stage is over: release its hold so the rail moves on.advance(): void— The stage is over now: jump the rail to the next stage's first leg (or complete the wave after the last).complete(): void— The wave is won: explosion (if any) and tally.hurt(cause: string): void— Lose a shield (or die at zero).data<T>(make: () => T): T— Module state (created on first use).dt: number— Seconds this fixed step covers.input: CockpitInput— The player's input this step.railInput: RailInput— Rail input the session will pass (modules may edit it).
StartChoice
interface StartChoice
A start choice on the select screen (Star Wars' three Death Stars, ESB's three planets).
wave: number— Wave to start at.label: string— Label (EASY, MEDIUM, HARD).bonus: number— Bonus paid at the end of the first wave completed.at: { u: number; v: number }— Where it sits, as a view-plane aim(u, v).radius: number— Aim radius that selects it.
StarWarsOptions
interface StarWarsOptions
Options for the Star Wars definition.
shields?: number— Starting shields (the cabinet: 6, 7, 8 or 9; default 6).bonusShields?: number— Shields added per Death Star (0-3; default 1, capped at the start count).difficulty?: DifficultyScale— Easy / Normal / Arcade (default normal).dogfight?: number— Dogfight seconds (21; 19.05 on a game's first wave).surfaceLaps?: number— Surface laps (10).trenchSlots?: number— Trench slots (162, 331,776 units).slots?: number— Simultaneous enemy ships (3).seed?: number— Seed.choices?: StartChoice[]— Start choices (default the cabinet's three Death Stars).firstWaveSurface?: boolean— Skip the surface on wave 1 (the cabinet does).stages?: (ctx: WaveContext, base: StageDef[]) => StageDef[]— Replace the wave builder (for custom missions on the same stages).
SurfaceObject
interface SurfaceObject
One object of a surface field.
forward: number— Distance into the field (0 .. lap).lateral: number— Lateral offset (right positive).kind: "tower" | "bishop" | "bunker"—'tower'fires forward and diagonally;'bishop'diagonally only;'bunker'is low and fires homing shots.seq: number— Lap from which it is active (0..3).
SurfaceStage
interface SurfaceStage extends StageDef
The surface stage definition.
type: "surface"— Stage type idsurface.layout: SurfaceObject[]— The field; it repeats everylapunits.lap: number— Field length (32768).wrap?: number— Lateral wrap span (65536): the field repeats sideways.laps: number[]— Highest activeseqper lap; the stage islaps.lengthlaps long. -1 adds nothing that lap.speed: { start: number; add: number; max: number }— Forward speed per frame: start, added per frame, maximum (256, 1, 1024).frameRate: number— Game frames per second (20).altitude: [number, number]— Altitude limits (512, 7168).startAltitude: number— Altitude at the start (7168).rates: [number, number]— Yoke rates at full deflection as fractions of forward speed: lateral, vertical (0.875, 0.47).bank: number— Bank at full yoke, radians (16.3 degrees).guns: number— Ground gun slots (by hardness).towers: { first: number; step: number; all: number }— Tower hat value: first, step, and the all-towers bonus (200, 200, 50,000).bunker: number— Bunker points (200).fireball: number— Fireball points (33).visible: [number, number]— Visibility: nearest and farthest drawn/hittable depth (512, 30720).showTowers: boolean— Show the tower messages and counter (false on the bunker-only wave).dive: { seconds: number; altitude: number; roll: number; speed: number } | null— The dive into the trench: seconds, altitude to reach, roll direction (+1/-1), speed per frame at the end.
TallyDef
interface TallyDef
End-of-wave tally rules.
objective?: number— Points for the wave objective (Star Wars: the exhaust port, 25,000).objectiveLabel?: string— Label for the objective line.perShield?: number— Points per shield left (Star Wars: 5,000).wave?: number— Points for completing a wave (ESB: 2,500).step?: number— Seconds between tally lines.
TrenchCell
type TrenchCell = 0 | 1 | 2 | 3
A wall cell: 0 empty, 1 decorative panel (shootable), 2 catwalk (blocks that half at that band), 3 wall gun.
TrenchFire
interface TrenchFire
Wall-gun fire table row.
mask: number— Window period minus one, in frames.chance: number— Chance an eligible gun fires in a window.guns: number— Shots in flight at once (all six once the port is in view).homing: boolean— Shots home on the player sideways (false on the cabinet's easiest setting: they aim at the sideline).
TrenchSlot
interface TrenchSlot
One slot along the trench: four bands per wall, top to bottom.
left: [TrenchCell, TrenchCell, TrenchCell, TrenchCell]— Left wall bands, top first.right: [TrenchCell, TrenchCell, TrenchCell, TrenchCell]— Right wall bands, top first.
TrenchStage
interface TrenchStage extends StageDef
The trench stage definition.
type: "trench"— Stage type idtrench.slots: TrenchSlot[]— The slots, nearest first.slot: number— Slot length (2048).length: number— Total trench length; the end wall stands here (331,776).portBack: number— The port lies this far before the end wall (4096).portLead: number— The port row is generated (and the Force bonus decided) this far before the port (24,576).width: number— Half-width to the walls (1024) and depth of the floor below the top (4096).depth: number— Floor depth.speed: number— Forward speed per frame (768) and frames per second (14.4 measured in the trench).frameRate: number— Game frames per second.limits: { x: number; y: [number, number] }— Lateral limit (511) and vertical limits (-3583, -257).rates: [number, number]— Yoke rates as fractions of forward speed: lateral, vertical (0.4375, 0.9375).startY: number— Altitude at the start (-3328 from the surface, -257 from space).hardness: number— Hardness index for this wave.fireTable: TrenchFire[]— Wall-gun rows by hardness (index clamped to the table).points: { turret: number; panel: number; fireball: number }— Points: turret 100, panel 50, fireball 33.force: number— Force bonus for this wave.visible: number— Visible distance for presenters and spawning (28,672).hints: "fireballs" | "catwalks" | null— First wave of a game: show the hint banners.portAhead: boolean— Show "EXHAUST PORT AHEAD" (the cabinet: first wave only).rerunHarder: number— Hardness added on each rerun.
WalkerStage
interface WalkerStage extends StageDef
Hoth: AT-ATs and AT-STs advance; shoot the head, tow-cable the legs or fly between them.
type: "walkers"— Stage type idwalkers.walkers: Array<"at-at" | "at-st">— Walkers in the stage, nearest first:'at-at'or'at-st'.spacing: number— Distance between walkers.cables: number— Tow cables (4).hits: { atAt: number; atSt: number }— Laser hits to kill an AT-AT's head and an AT-ST.points: { atAt: number; atSt: number; shot: number; between: number }— Points: AT-AT, AT-ST, shot; progressive fly-between bonus step (5,000).fireEvery: number— Seconds between each walker's shots.flight: { speed: number; altitude: [number, number]; rates: [number, number] }— Flight.
WaveContext
interface WaveContext
What a wave builder is told.
wave: number— Displayed wave number.hardness: number— Hardness index for this wave (0..15).first: boolean— First wave of this game.startWave: number— The wave the game started at.difficulty: DifficultyScale— The difficulty scale.seed: number— Seed for this wave's generated content.
WaveDef
interface WaveDef
One wave: its number and stages, in order.
wave: number— Displayed wave number.stages: StageDef[]— Stages.


