Rally RaidNavigator

Trophée Atlas 1977
Alpha — all 11 phases complete Last build: 2026-06-12
218
Kilometres
5
Stages
32
Crews
52
Modules
8.2k
Lines of Code

What is Atlas Trophy

A 1977 desert rally-raid through Morocco's High Atlas mountains. You ride shotgun as the navigator — the AI pilot (Jean-Michel "Michou") drives. Your job: place waypoints on the paper map, read the roadbook, manage the instruments, and keep the crew alive across five days and 218 km of sand, rock, fesh-fesh, and mountain passes.

Built as a single-page browser game. No server, no install. Three.js + Rapier3D physics + Web Audio waveguide engine synthesis. Real SRTM elevation data from the Atlas mountains.

Tech Stack

Three.js r184 Rapier3D Web Audio API AudioWorklet SRTM / Terrarium DEM ES Modules Vite Canvas + SVG

Player Flow

Splash Carte Générale Liaison Paper Map Stage Bivouac Day N+1

5-day campaign persisted in localStorage. Day 5 → Arrivée Finale + general classification + Nouveau Rallye.

Architecture & Modules

52 ES modules across 18 directories, zero framework. Each system is isolated: physics has no gameplay coupling, rendering is testable in Node, AI is seeded and reproducible.

physics/
Rapier3D world, Vehicle class (chassis + 4 wheels, 6-DOF), gear mapping, slip/drift, rollover recovery
world.js · vehicle.js · vspec.js
terrain/
Chunked streaming (200m tiles), procedural Perlin + DEM blend, marching-squares contours, surface zones
height.js · chunked.js · dem.js · contours-svg.js
nav/
PilotAI (mood state machine, feature-aware steering), navigator waypoints, dialogue controller with mood/trust gates
pilot.js · nav.js · dialogue.js · geo.js
cockpit/
Smiths gauges (SVG, 240° sweep), Halda tripmeter, roadbook scroll, 7 warning lamps, 5 toggle switches
hud.js · roadbook.js · systems.js
rally/
5-day campaign loop, 31-team field sim (2 Hz seeded tick), localStorage persistence, incident consequences
stages.js · state.js · field.js · teams.js
audio/
Waveguide V8 synthesis (AudioWorklet), RPM from gear+speed, surface/wind/impact procedural layers
audio.js · jukebox.js · vendor/
dialogue/
Two voice packs: VF (Le Terrible, fr-FR) + VQ (Abitibi Express, fr-CA). BD phylactères with mood/trust gates
packs.js
vehicles/
7-vehicle fleet, palette-driven vertex-color livery baking, per-vehicle .vehicle.json canonical specs
assets.js · livery.js
map/
SVG paper map with tap-to-place waypoints, zoom/pan, contour overlay, grid and corridor rendering
papermap.js · contours-svg.js
game/
Input (keyboard + gamepad + touch), 6-preset camera rig, stuck detection, incident logging
input.js · camera.js · stuck.js · incidents.js
shell/
Screen system: splash, genmap, liaison, bivouac, planning. CSS fade transitions, mutually exclusive
screens.js
forge/
Dev-time asset generator: rocks, vegetation, ruins, vehicles. Seeded RNG, recipe export, GLB pipeline
forge-main.js · gen/*.js · recipe.js · export.js

Key Design Decisions

Phase Status

P1
Physics Core
Complete
P2
Game Parity
Complete
P3
Cockpit
Complete
P4
Shell + Planning
Complete
P5
World Polish
Complete
P6
Audio
Complete
P7
Cameras + Visual
Complete
P8
Vehicles + Field
Complete
P9
Comic Dialogue
Complete
P10
Day Loop
Complete
P11
Content
Complete
Forge
Asset Gen
Gate 2 Closed
Forge M3
Vehicles
In Progress
Forge M4
Scatter
Deferred

Changelog

P1Physics Core2026-06-11
  • ES module extraction — all physics isolated in src/physics/
  • Real gravity (G = −9.81 m/s²) with full Landy re-tune
  • Surface contract C6: surfaceAt() returns {grip, roll, label}
  • 5×5 km proving ground with 6 surface zones
  • Rapier3D rigid body vehicle: chassis + 4 wheels, suspension springs (springK 62000)
  • Timer-driven render loop (hidden-tab safe — setInterval + rAF)
world.js · vehicle.js · vspec.js · config.js

Gate probes: static sag 32.9%, corner roll 24°, jump airtime 0.18s, top speed ~151 km/h

P2Game Parity2026-06-11
  • Wired modular physics (P1) into game entry point
  • Le Terrible drives autonomously; player navigates
  • PilotAI mood state machine: calm → fast chatter → drift → panic
  • Navigator waypoint system with cone meshes (yellow/gold/brown) + nudge rings
  • Dialogue system: voice line triggers on game events (obstacles, speed, finish)
  • Camera follow with velocity-damped yaw, shake accumulation, FOV breathing
input.js · camera.js · nav.js · pilot.js · dialogue.js
P3Cockpit Alive2026-06-11
  • Full instrument panel: Smiths-style gauges (SVG, 240° sweep), Halda tripmeter
  • Vehicle systems simulation: water temp, oil temp/pressure, voltage, fuel consumption
  • Roadbook scroll with tulip SVGs, hazard labels, distance cones, altitude
  • 7 warning lamps (oil, water, fuel, battery, brake, alternator, overheat)
  • 5 toggle switches + CTIS panel + compass heading
  • Overheat cuts engine power; damage model (engine, radiator, brakes, electrical, steering, suspension)
hud.js · roadbook.js · systems.js
P4Shell + Planning2026-06-11
  • Screen system: registerScreen() / gotoScreen() with CSS fade transitions
  • SVG Paper Map: grid, corridor, features, start/finish, compass, scale bar
  • Tap-to-place waypoints on the map → waypoints feed Nav directly (no RECON step)
  • Flow: Splash → Planning (map) → Stage (3D boot deferred until needed)
  • Corridor fallback when 0 waypoints placed
screens.js · papermap.js · contours-svg.js
P5World Polish2026-06-11
  • Surface authoring: plateau (grip 0.95), sable (0.84), oued (0.72), roche (0.55), fech-fech (0.38)
  • Water fording: wadiDepthAt() with closest-point-on-segment, quadratic blend, drowning ramp
  • Bush brush-through: tagged props (no collider), velocity damping on contact
  • Distribution: ~69% sand, ~21% plateau, ~8% fech-fech, plus STAGE feature overrides
height.js (featureAt) · systems.js (drowned ramp)
P6Audio Engine2026-06-11
  • Waveguide physical modelling via AudioWorklet — V8 8-cylinder synthesis
  • RPM derived from vehicle gear + speed (unified gear ladder per vehicle type)
  • Fallback chain: AudioWorklet → sample ladder (25 WAVs) → procedural oscillators
  • LPF at 3200 Hz, shift blip envelope on upshift
  • Surface crunch, wind, impact, backfire layers coded (disabled pending tuning)
audio.js · jukebox.js · vendor/waveguide.js
P7Cameras + Visual Consolidation2026-06-11
  • Camera preset system: Classic, Rally (h24/b18/fov48), Overview (h38/b22/fov42)
  • Speed-reactive FOV, airtime hold, velocity-damped yaw follow
  • Time-of-day wiring (?tod=0..1, 0=dawn, 0.5=noon, 1=sunset)
  • Forge Gate 1 audit pass: trunk palette lift v1 → v2
camera.js (CONFIG.cam.presets) · forge palette.js
P8Vehicles + Field + Incidents2026-06-12

W1 — R4 Sinpar Hero Vehicle

  • CONFIG.r4: mass 820, springK 25500, enginePower 7000, gearKmh [2,16,38,65,95]
  • Vehicle selector via ?veh= URL param

W2 — Jump/Landing + Rollover Recovery

  • Landing damper: extra rebound after >0.4s airtime
  • Air auto-level: body-up → world-up alignment, input-gated per axis
  • Flop recovery: stuck-on-side detect (75°, 3s), _rightCar() uprights in place

W3 — Deep Sand + STUCK Machine

  • Sand physics: vFloat 45 km/h, dragK 0.30, fesh-fech ×2
  • State machine: FREE → BOGGED (rocking) → DIGGING (E-hold, 75s cooldown)

W4 — 31-Team Field Simulation

  • All 31 NPC crews from the 1977 Engagés bulletin, racing in real-time (2 Hz seeded tick)
  • Staggered starts (12s × number order), encounter HUD (<60m), E=AIDER rescue
  • Standings by net time, relations tracked both ways

W5 — Pilot Behavior

  • Dune commit, crest discipline, rookie errors, morale/obedience systems

W6 — Incidents

  • OVERHEAT, LOST, STUCK, TOW + camion-balai ASA fallback

Vehicle Fleet Overhaul (Session 3)

  • 7 vehicles remapped to all-low-poly GLBs (40 MB photogrammetry scans retired)
  • livery.js palette-driven vertex-color bake pipeline
  • Per-vehicle .vehicle.json canonical specs with real gravity (9.81)
  • NPC 180° heading fix (all models face −Z at identity)
  • Truck STL Z-up orientation fix (Y-longest-axis detection)

Deep Audit (∼30 findings fixed)

  • Double frame loop eliminated (interval yields when rAF alive)
  • Field: rescuer-ahead teleport fixed, divert self-release (240s), seeded RNG per team-tick
  • Vehicle: sand-drag clamped, brake scales with input, landing damper rebound-only
  • HUD: digitStrip built once + mutates on change (was ~3000 nodes/s), roadbook cached
config.js · stuck.js · field.js · incidents.js · livery.js · assets.js
P9Comic Dialogue2026-06-11
  • Two voice packs: VF (Le Terrible — Michou/NAV, fr-FR) and VQ (Abitibi Express — Ti-Guy/Réal, fr-CA with ?crew=vq)
  • Dialogue engine rewritten: mood gates [calm/hot/panic/fatigue], trust gates (>0.6 / <0.4)
  • Draw-without-replacement per pool, reset per stage, one live bubble per side
  • BD phylactères: white ovals (Nunito 700/900), SHOUT = Bangers starburst (two-layer clip-path star), sulky = dashed border
  • Pilot-LEFT / nav-RIGHT positioning, projected each frame to hug the car
  • Reading time: max(3.5s, 1.5s + 65ms/char)
  • Set-pieces: roman-photo overlay, click-to-advance, trust deltas on exit
  • bold markdown parsing → <b> tags
packs.js · dialogue.js · index.html (CSS)
P105-Day Campaign Loop2026-06-11
  • Five specials: SS1 Nfis (22 km), SS2 Azzadene (38 km), SS3 Tichka (28 km), SS4 Gorges-Reg (48 km), SS5 Hamada (32 km)
  • Per-day terrain overrides applied to both config objects (two-config trap: height.js reads src/config.js)
  • Rally state in localStorage: per-day times, penalties, relations, incidents, parts (3), carried damage, pilot learning
  • Bivouac screen: étape + général classifications, repair spending parts, journal entries
  • Day 5 → ARRIVÉE FINALE + rank + NOUVEAU RALLYE (clearRally())
  • Real DEM landscapes for all 5 stages (276 SRTM tiles): J1 datum 846m, J5 datum 1441m, vScale 0.5–0.65
  • Boot shows « Chargement du relief réel… »; procedural fallback on failure
  • Hero default = r4 (Chastel 4L Sirocco, équipage n° 22)
stages.js · stage.js · state.js · dem.js
P11Content & Narrative2026-06-11
  • 5 stage datasets boot-verified (SS3 fech-fech zone, SS4 21 roadbook rows, SS5 crisis + flat hamada)
  • Roadbook/tulip fix: nearestFeature read f.x/f.z (always NaN — hazards NEVER fired since P3) → featurePos() helpers
  • Narrative beats: J1 tutorial overheat (km 16.5), J5 mechanical crisis (km 26 → OVERHEAT = stop+cool vs press-on)
  • Set-pieces wired once-per-rally: pas_perdus on first DIGGING, gue_de_trop on drowned, pourquoi at bivouac J2, réconciliation at bivouac J4 if day rank ≤12
  • Goat gag seeded per stage (60–240s, stage-stable)
  • Canon update: pilot = Jean-Michel « Michou », NPC n° 22 = Lemoine/Davoust, player = n° 34 (VF) or n° 36 (VQ)
stages.js (datasets) · nav.js (featurePos) · dialogue.js (set-pieces)
ForgeAsset Generator (M1 + M2)2026-06-11

M1 — Shell + Rocks

  • Forge UI: tabs (rocks | vegetation | ruins | vehicles | scatter), OrbitControls viewport
  • Rock generators: boulder, scree, mesa, arch — all deterministic, validator-green
  • Seeded RNG (mulberry32), recipe format, GLB export pipeline
  • Gate 1: 7 findings, all closed (validator --regen, bbox ±1%, arch caps)

M2 — Vegetation + Ruins

  • Palm (408 tris, phyllotaxis), acacia (228 tris), scrub (60 tris), tuft (7 tris)
  • Ruins: wall slab, archway, column, crenellated, plank bridge (60–300 tris each)
  • Gate 2: 6 findings, all closed (erodeTop fix, umbrella W/H, palette v2 lift)

M2.5b — Full Reference Import

  • 120 imported entries (17 Quaternius + 62 BV + 41 CP) + 13 procedural
  • DAE parser (Collada, Z-up), FBX parser, height-based trunk/canopy coloring
  • 30/30 --regen green on palette atlas-v2
forge-main.js · gen/rocks.js · gen/vegetation.js · gen/ruins.js · gen/imported.js
Forge M3Procedural VehiclesIn Progress
  • 4 archetypes: twobox, roundedHatch, pickup, cabover
  • Loft algorithm: cross-section polygon → swept surface
  • Accessories: roofRack, spare, jerryCans, lampPods, bullBar, sandLadders, flag, exhaustStack
  • Livery zones: body paint, stripe band, glass, bumper, roof
  • Contract: .vehicle.json stub export, registerSplitVehicle() round-trip
gen/vehicles.js (planned)

Roadmap

Next Forge M3 — procedural vehicle bodies (hero r4, 4 archetypes)
Next Departure order — fastest-first from prior stage classification, 30s intervals
Next Liaison as drivable stage — road terrain + liaison driving mode
Later Forge M4 — scatter system (biome presets, Poisson-disk sampling, <100 draw calls)
Later Set dressing — bivouac props, villages, kasbahs, gorge walls as real geometry
Later TTS voice synthesis — corpus designed for fr-FR/fr-CA voices, not yet wired
Later Character portraits for P9 dialogue scenes
Later Authored relief profiles — lacets, gorges as actual canyons (DEM + Forge pass)