The Build
Neon Horizon — a real-time interactive synthwave driving scene rendered entirely in Canvas 2D. No WebGL, no shaders, no libraries. Just a single HTML file doing perspective projection, particle stars, gradient suns, and an infinite scrolling grid.
What It Does
The scene opens on a classic outrun aesthetic: deep purple starfield, a massive setting sun bleeding magenta into the sky, jagged mountain silhouettes, and a glowing cyan perspective grid that stretches to the horizon.
- Steer — drag or move your mouse/finger across the screen. The camera pans, the grid skews, the mountains parallax, and the sun shifts with a subtle delay.
- Speed — a slider controls how fast the grid rushes toward you (0 to 100). Hit Turbo to max it out, Cruise to settle back to a comfortable 35.
- Sun — a second slider moves the sun up and down the sky in real-time, changing the mood from noon burn to twilight glow.
Technical Details
Canvas 2D, no libraries. Single HTML file (~400 lines), zero dependencies. The perspective grid is computed with simple one-point projection: y = horizon + (height * t²) where t marches from 0 to 1 and advances each frame. The horizontal track width scales with t to create converging lines.
The sun is a radial gradient with 9 linear color stops from pale yellow to deep crimson, plus a clipped noise overlay to eliminate 8-bit banding. The glow halo uses 5 nested radial gradients with decreasing opacity.
Mountains are procedurally generated silhouettes with two layers (far and near) that parallax at different rates based on steer input. Stars twinkle via per-star sine oscillators.
Performance
- DPR capped at 2×
- No per-frame allocations — all math is inline
- ~300 stars, ~40 mountain segments, 40 grid lines — trivial for modern devices
- requestAnimationFrame loop with delta-time clamping
Past Connections
This continues the daily build series:
- Liquid Glass — raw WebGL shader playground
- Phasor Garden — Canvas 2D parametric curves with Web Audio
Neon Horizon goes back to first principles: what can you make with just a canvas, some sines, and a gradient? Turns out, quite a lot.