skifree singleton
skifree · gamesThe classic SKIFREE (ski downhill, dodge trees / rocks / jumps, get chased and EATEN by the abominable snowman) as a CV-controlled game module — a thin wrapper around the upstream skifree.js engine (MIT, Daniel Hough 2013). Single-instance per rack (maxInstances:1). Two bipolar CV inputs (x / y, −1..+1) synthesize the mouse cursor the skier steers TOWARD: x = cursor X across the canvas (0 = left edge, +1 = right edge), y = cursor Y (the skier always heads downhill; cursor position sets the steering angle + speed). When x and y are BOTH unpatched, mouse steering is available on the module's own surface: CLICK the slope to take the controls, then move the pointer over it and the skier heads for wherever you are pointing (pointing BELOW the skier is what sends it downhill). Any patched CV OVERRIDES the mouse, on the next pointer move, without a mode to switch (the factory writes the CV cursor each scheduler tick and the surface stops writing). The pointer position is mapped as a RATIO of the displayed picture's rect, so the 320 px dock slope and the 104 px lane thumbnail mean the same gesture; the vendored bundle's own enableMouse path is NOT used, because its handlers take their rect from the factory's detached canvas and therefore fed raw viewport pixels into a 0..320 space. One gate output: a rising-edge 10 ms pulse on every CRASH (hitting a tree / rock / snowboarder / failed jump) OR when the yeti EATS the skier — hooked to the engine's hasHitObstacle callback (upstream fires it for crashes and, via isEatenBy, for eats), so the game becomes a trigger source for envelopes / sequencers. One video output (out): the game canvas mirrored each video frame via the cross-domain audio→video bridge — patch SKIFREE → VIDEO OUT / BENTBOX / any video module to send the ski-slope render downstream (mirrors the DOOM `out` pattern). The game itself belongs to the NODE — the factory loads the bundle, builds the controller against a DETACHED canvas and disposes it when the node leaves the graph — so a rack nobody has expanded is still skiing, still crashing and still firing its gate, and the faceplate BLITs from that canvas rather than owning it. The faceplate carries the slope in two places: a steerable 320 px picture at the head of the dock full view, and a read-only thumbnail on the lane tile, both with a SCREEN switch semantic that stops the PICTURE and never the game. The `out` video port is the way to send the slope anywhere else. No audio worklet — the gate is a ConstantSourceNode pulsed on the event (PONG's pattern); the game logic runs at rAF cadence inside the bundle. Bundle committed pre-built at /skifree/skifree.bundle.js (~24 KB, esbuild IIFE of the upstream js/ classes + a thin embed wrapper); sprite sheets at /skifree/*.png. See packages/web/native/skifree/README.md for the regeneration recipe + attribution.
the faceplate
inputs
| id | cable | what it does |
|---|---|---|
x | cv | Bipolar CV (−1..+1) → the cursor's X position the skier steers toward. −1 = far left, 0 = straight down the fall line, +1 = far right. Read at scheduler-tick rate (a continuous position, not a gate). Patching it overrides mouse steering on the faceplate. control voltage (CV) |
y | cv | Bipolar CV (−1..+1) → the cursor's Y position the skier steers toward. −1 = top, 0 = center, +1 = bottom — pulling the cursor lower makes the skier point more steeply downhill (faster). Continuous position, read each tick; patching it overrides the mouse. control voltage (CV) |
outputs
| id | cable | what it does |
|---|---|---|
gate | gate | Fires a 10 ms pulse on every crash event — hitting a tree, rock, snowboarder, or a failed jump — AND when the yeti finally eats the skier. A rising-edge trigger you can route to a crash sound, a drum hit, or a sample; the rhythm of pulses tracks how cleanly (or not) the run is going. gate / trigger; trigger — fires once per rising edge |
out | video | The live game canvas as a cross-domain video source — each video frame the skier/mountain image is blitted into the audio→video bridge. Patch it into VIDEO OUT, BENTBOX, or any video module to display or further process the game. RGB video stream |
source
skifree.ts on GitHub.