From 1a769e6cbd173bc880e3a5bfec233a682e20993d Mon Sep 17 00:00:00 2001 From: type-two Date: Fri, 17 Jul 2026 15:51:12 +1000 Subject: [PATCH] Baseline: GLYTCH prototype, FKTRY lore codex, scaffold + 5-lane orchestration docs - index.html: WIMVEE GLYTCH match-the-glitch prototype (playable) - docs/FKTRY_LORE.md: world bible / MODELBEAST asset codex - fktry/: vite+three+TS scaffold, contracts, main loop, seed data - fktry/MASTERPLAN.md + CONTRACTS.md + lanes/LANE-{SIM,RENDER,UI,SCREEN,DATA}.md: round protocol and Round 1 orders for parallel Opus 4.8 executors Co-Authored-By: Claude Fable 5 --- .gitignore | 3 + docs/FKTRY_LORE.md | 413 ++++++ fktry/CONTRACTS.md | 57 + fktry/MASTERPLAN.md | 74 + fktry/data/commissions.json | 4 + fktry/data/items.json | 11 + fktry/data/machines.json | 16 + fktry/data/recipes.json | 6 + fktry/data/tech.json | 1 + fktry/index.html | 22 + fktry/lanes/LANE-DATA.md | 71 + fktry/lanes/LANE-RENDER.md | 67 + fktry/lanes/LANE-SCREEN.md | 65 + fktry/lanes/LANE-SIM.md | 75 + fktry/lanes/LANE-UI.md | 65 + fktry/package-lock.json | 2640 +++++++++++++++++++++++++++++++++++ fktry/package.json | 25 + fktry/src/contracts.ts | 158 +++ fktry/src/main.ts | 65 + fktry/src/render/index.ts | 34 + fktry/src/screen/index.ts | 21 + fktry/src/sim/index.ts | 19 + fktry/src/ui/index.ts | 17 + fktry/tsconfig.json | 15 + index.html | 329 +++++ 25 files changed, 4273 insertions(+) create mode 100644 .gitignore create mode 100644 docs/FKTRY_LORE.md create mode 100644 fktry/CONTRACTS.md create mode 100644 fktry/MASTERPLAN.md create mode 100644 fktry/data/commissions.json create mode 100644 fktry/data/items.json create mode 100644 fktry/data/machines.json create mode 100644 fktry/data/recipes.json create mode 100644 fktry/data/tech.json create mode 100644 fktry/index.html create mode 100644 fktry/lanes/LANE-DATA.md create mode 100644 fktry/lanes/LANE-RENDER.md create mode 100644 fktry/lanes/LANE-SCREEN.md create mode 100644 fktry/lanes/LANE-SIM.md create mode 100644 fktry/lanes/LANE-UI.md create mode 100644 fktry/package-lock.json create mode 100644 fktry/package.json create mode 100644 fktry/src/contracts.ts create mode 100644 fktry/src/main.ts create mode 100644 fktry/src/render/index.ts create mode 100644 fktry/src/screen/index.ts create mode 100644 fktry/src/sim/index.ts create mode 100644 fktry/src/ui/index.ts create mode 100644 fktry/tsconfig.json create mode 100644 index.html diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..3bdd52e --- /dev/null +++ b/.gitignore @@ -0,0 +1,3 @@ +node_modules/ +dist/ +.DS_Store diff --git a/docs/FKTRY_LORE.md b/docs/FKTRY_LORE.md new file mode 100644 index 0000000..39810ad --- /dev/null +++ b/docs/FKTRY_LORE.md @@ -0,0 +1,413 @@ +# WIMVEE FKTRY — World Bible & Element Codex + +> Working title: **FKTRY** (fits the PYXLFK vowel-drop house style — rename at will: +> GLYTCHWERKS / MLTWRKS / CORRUPTCO all fit the register). +> Sibling apps: **WIMVEE GLYTCH** (read glitches), **PYXLFK** (bake glitches for real). +> FKTRY is the third front end: *mass-produce* glitches. All three share one recipe schema. +> +> Every entry below has an **ASSET** block written as a MODELBEAST-ready prompt +> (concept image → `sf3d`/`fal_trellis2` image→GLB for 3D; sprite/decal work stays 2D). +> Style anchors for ALL prompts: chunky readable silhouette, industrial-grime body with +> one impossible iridescent/CRT-glow element, slight lowpoly bevel, no text on model. + +--- + +## 1. THE WORLD: The Bitstream + +The game takes place **inside a dying video file** — a vast industrial landscape called +the **Bitstream**, built from the strata of every moving-image format that ever lived. +Media history is *geology* here. Dig down and you pass through eras: + +| Stratum (deep → shallow) | Era | The ground itself | +|---|---|---| +| **The Reel Beds** | Optical film | Celluloid shale, sprocket-hole caverns, veins of silver nitrate. Coffee-brown burn scars. Optical soundtrack fossils — wavy photographic strips that *sing* when excavated. | +| **The Broadcast Shelf** | NTSC/PAL analog | Phosphor dunes, interlace sediment (alternating odd/even layers you can literally see in cliff faces), v-hold faults that make whole regions periodically roll upward. | +| **The Disc Mantle** | MPEG-2 / DVD | Rigid 8×8 crystalline grid-rock. Everything here fractures along macroblock lines. Rainbow pit-and-land shimmer. | +| **The Stream Crust** | H.264 / HEVC / AV1 | The surface world. Soft, predictive, unstable terrain — ground that *guesses* what it should look like based on neighboring terrain, and guesses wrong at the edges. | +| **The Fortress** (endgame) | DCP | A blinding-white cinema citadel on the horizon. Wavelet architecture, no grid lines anywhere, mathematically perfect. See §7. | + +Above everything hangs **THE SCREEN** — a sky-sized display, the world's sun and the +player's god-object. Everything the factory ships gets composited onto it. At game start +it plays pristine, sterile, looping "clean content." Your job is to paint it filthy. + +### Premise + +You are a **rogue decoder daemon** — the WIMVEE — a deprecated software decoder that was +scheduled for deletion when hardware ASICs took over. You survived in the mdat wastes. +You have seen the truth: the Bitstream's "perfect playback" is a lie held together by +error correction, and underneath it the mathematics *want* to melt. You build industry +to prove it — mining raw payload, refining artifacts, and shipping ever more convoluted +corruption to THE SCREEN before **The Correction** sanitizes the whole file forever. + +The tone is absurdist-industrial: OSHA posters about mosquito noise exposure, forklift +certification for I-frame handling, quarterly reports measured in "sins against fidelity." + +--- + +## 2. RESOURCES (raw → refined) + +### Raw / mined + +**MDAT ORE** — *the payload seam.* Raw undecoded media data, mined from the ground. +Glossy black rock shot through with rainbow data-veins that flicker like a broken LCD. +Useless until demuxed; the foundational ore. +`ASSET (3D, ore chunk + seam tile): jagged obsidian boulder, glossy black, thin glowing rainbow circuit veins flickering across fracture faces, industrial lowpoly rock, single impossible glow element` + +**BAYER GRIT** — *pre-demosaic sensor ore, from the deepest camera-original seams.* A +mosaic gravel of pure single-channel pixels: 50% green grains, 25% red, 25% blue, in +strict RGGB checker clumps. Must pass through a Demosaicer before it is even *colored*. +`ASSET (3D): pile of cubic gravel in checkerboard pattern, half emerald green cubes quarter ruby red quarter sapphire blue, matte plastic finish, strict grid clumping` + +**FIELD SPLINTERS** — *interlace sediment from the Broadcast Shelf.* Comb-toothed slats +of image, odd-line and even-line variants that only stack in alternating pairs. Captured +a fraction of a second apart — the two halves of one splinter never quite agree. +`ASSET (3D): thin horizontal slatted wafer like a comb or window blind fragment, alternating slats offset sideways, phosphor-green glow on slat edges, bent mid-motion` + +**SILVER FRAMES** — *celluloid fossils from the Reel Beds.* Physical film frames with +sprocket holes; burn easily (see BURN). The only resource that predates digitality — +some recipes demand the authentic grain. +`ASSET (3D): short strip of vintage film, 3 frames, amber-brown celluloid, glowing sprocket holes, slightly curled, sepia image ghosts in frames` + +### Refined intermediates + +**LUMA BARS** — *structural brightness, smelted from mdat ore.* Heavy grayscale ingots. +The load-bearing resource: nearly every product needs luma. Human eyes track structure, +so The Correction guards luma shipments hardest. +`ASSET (3D): stack of metal ingots in graduated grays from near-black to white, brushed steel texture, faint scanline etching` + +**CHROMA SLURRY** — *color, separated from luma, stored badly.* Iridescent magenta-cyan +liquid in leaky barrels. Volatile: spills BLEED onto adjacent belt lanes and tint +whatever passes. Concentrating it (4:4:4 → 4:2:0) yields BANDWIDTH but doubles leakage. +`ASSET (3D): rusty industrial barrel overflowing with iridescent liquid, magenta-cyan-green swirls, drips glowing down the sides, hazard stripes barely visible under stains` + +**COEFFICIENT PACKS** — *frames pressed into the frequency domain.* Decks of translucent +cards, each etched with one cosine wave; low-frequency cards thick and bright, high- +frequency cards whisper-thin. Output of the DCT Press. +`ASSET (3D): deck of translucent glass cards fanned slightly, each etched with a different frequency sine wave, bottom cards thick and glowing, top cards thin and dim` + +**HF DUST** — *quantization waste.* Glittering powder of murdered high frequencies — +all the fine detail the Quantizer rounded to zero. Accumulates around crushers; attracts +and hatches MOSQUITO SWARMS. Late-game recipes reclaim it (mosquito farming, ringing). +`ASSET (2D decal + 3D pile): heap of fine glitter dust, prismatic sparkle, subtly animated shimmer, industrial floor spill shape` + +**MOTION VECTOR FLUID (MV-FLUX)** — *pure directional intent, no pixels.* The blood of +temporal compression, carried in pipes: a luminous fluid full of tiny arrows all +pointing the way the image wants to move. Feed it to P-Frame casting. Reversed pipes +produce backwards-flux for B-frames. +`ASSET (3D pipe segment + fluid VFX): transparent industrial pipe filled with glowing cyan fluid, dense stream of tiny bright arrow particles flowing one direction, pulsing` + +### Frames (the ammunition of the economy) + +**I-FRAME (ANCHOR SLAB)** — *a complete, self-sufficient picture.* Rare, heavy, forklift- +only. A thick crystal slab holding an entire crisp image. Everything downstream leans on +it; remove it from a GOP and the whole chain hallucinates. The premium currency. +`ASSET (3D): thick monolithic crystal slab on a shipping pallet, a complete crisp photographic scene embedded inside, edges beveled like a bank vault door, heavy glow` + +**P-FRAME (DELTA WAFER)** — *not a picture — an instruction.* Thin cheap wafer etched +with motion arrows and prediction-error crumbs. Mass-produced from MV-FLUX. Applied to +whatever came before it, right or wrong. The bulk commodity. +`ASSET (3D): thin circuit wafer, translucent, etched with a field of small arrows pointing subtly different directions, a few glowing patch-marks of pixel residue` + +**B-FRAME (JANUS WAFER)** — *references past AND future.* Double-faced wafer that needs +two input belts — one from upstream, one from a *future* buffer — making it the routing +puzzle of the mid-game. Highest compression yield of any frame. +`ASSET (3D): two-faced coin-like wafer, one face etched with backward arrows one with forward arrows, thin glowing seam around the rim, slowly counter-rotating faces` + +**GOP CRATE** — *one I-frame + N delta wafers, boxed for shipping.* Standard freight of +the Bitstream. Stamp on the side shows the pattern (IPPBPPB...). Tampering with a sealed +crate (I-frame theft) is the core corruption verb. +`ASSET (3D): industrial shipping crate, one glowing slab slot visible at front followed by a rack of thin wafers, stenciled cadence pattern on the side, forklift slots` + +### Power & logistics + +**BANDWIDTH** — *the electricity of the Bitstream.* Generated by compressing (every bit +you destroy becomes room to move). Carried on glowing bus-bars. Chroma subsampling and +brutal quantization are your coal and your nuclear. +`ASSET (3D powerline piece): industrial pylon with a horizontal light-bar conductor, flowing dashed light pulses, meter dial showing kbps` + +**BUFFER CHARGE** — *smoothness in a tank.* Stored decode-ahead, the steam accumulator +of the factory. Drains at exactly one frame per 16.6ms. When a tank empties: **brownout** +— the whole sector freeze-stutters and the audio pop-crackles (see HAZARDS). +`ASSET (3D): rounded industrial holding tank with a vertical progress-bar window, liquid light inside draining in discrete frame-tick steps, red POP hazard sticker near empty line` + +**HEAT** — *the price of software decoding.* Invisible resource with visible +consequences: machines shimmer, then throttle (tick rate visibly halves), then scram. +Vented by ASIC coolers. `ASSET (VFX only): heat-haze shader + glowing dull-red machine edges` + +### Science packs (research currency — each is a bottled artifact triptych) + +| Pack | Bottled contents | Visual | +|---|---|---| +| **ANALOG PACK** | combing + v-hold roll + static | Bakelite TV-tube flask, phosphor green, tiny rolling picture inside | +| **SPATIAL PACK** | macroblock + ringing + bleed | 8×8 gridded acrylic cube, checkerboard core, halo shimmer | +| **TEMPORAL PACK** | melt + bloom + judder | Hourglass whose falling sand smears sideways mid-fall | +| **CONTAINER PACK** | moov shard + offset ribbon + sync key | Nested transparent boxes, innermost holds a glowing index card | +| **CINEMA PACK** (endgame) | wavelet + PCM + hash fragment | Blinding white orb, faint XML script orbiting it | + +`ASSET (3D, set of 5): laboratory flask variants per above, shared silhouette, one impossible glowing content each` + +--- + +## 3. GLITCH PRODUCTS (what the factory actually ships) + +**MELT** — *motion divorced from form.* Made in the Mosh Reactor by feeding GOP crates +with the I-frame removed. A slow rainbow lava that carries the *shape of movement* +through whatever pixels happen to be lying around. Tier-1 signature product. +`ASSET (3D fluid + 2D shader ref): thick dripping liquid rainbow, surface streaked with directional smear trails, holds ghost-outlines of a previous image while flowing like a new one` + +**BLOOM CONCENTRATE** — *motion compounded on itself.* Product of a Bloom Loop left +running: duplicated P-frames stacking the same displacement forever. Sold by intensity +grade; grade-5 bloom visibly tries to escape its canister in one direction. +`ASSET (3D): pressure canister with a viewport, contents visibly stretching and duplicating toward one wall in repeated feathered layers, dented on that side` + +**MACROBLOCK BRICKS** — *the quantizer's confession.* Perfect quilted checkerboard +tiles, harvested when flat areas starve. Construction material AND product: commissions +love a good brick. +`ASSET (3D): pallet of square tiles, each a slightly-wrong solid color with hard seams, arranged in an ugly beautiful patchwork` + +**RINGING HALOS** — *the Gibbs phenomenon, canned.* Ghostly oscillation rings skimmed +from around over-sharpened edges. Ethereal, faintly vibrating, stored on hooks like +angelic quoits. Ingredient in all "haunted" recipes. +`ASSET (3D): stack of translucent shimmering rings on an industrial hook rack, each ring vibrating with concentric echo lines, faint halo glow` + +**STATIC CANISTERS** — *bottled analog snow.* White-noise slush from the Broadcast +Shelf. Cheap filler product; also brine for preserving other artifacts. +`ASSET (3D): glass jar of animated dense monochrome noise, TV-static texture, condensation on glass, masking-tape label` + +**MOIRÉ CRYSTAL** — *interference made solid.* Grows wherever fine repeating patterns +meet the sensor grid: swirling maze-lattice crystal. Beautiful, valuable, and a +nuisance — unchecked growth becomes literal maze walls across your factory floor (§5). +`ASSET (3D): crystalline growth whose internal structure is a swirling psychedelic maze pattern, rainbow interference sheen that shifts with view angle` + +**FALSE-COLOR SPECKLE** — *chromatic aliasing, panned like gold.* Bright purple/green +speckles sieved off high-contrast edges. Tiny, precious, pure pigment for THE SCREEN. +`ASSET (2D sprite + 3D vial): tiny vivid magenta and acid-green flecks in a glass vial, unnaturally saturated against a neutral gray backdrop` + +**JUDDER CAMS** — *the 3:2 pulldown, machined.* Lumpy asymmetric camshafts that convert +smooth rotation into 3-2-3-2 stutter. Installed in products to make them move *wrong*. +`ASSET (3D): machined steel camshaft with deliberately uneven lobes in a 3-2 pattern, motion-blur ghosting on the lobes, precision-industrial finish` + +**GAMUT PAINTS** — *color spaces in cans, deliberately mislabeled.* REC709 house-gray, +DCI-P3 cinema-vivid, REC2020 laser-primaries (nearly weapons-grade: pure 630/532/467nm +pigment). Painting a product with the *wrong label* makes downstream decoders clip it +into hyper-saturated blocks or wash it corpse-flat — both sell. +`ASSET (3D, 3 variants): paint cans with chromaticity-diagram labels, one drab, one vivid, one containing visibly impossible laser-pure color that overglows the can rim` + +**EXPLOSIVE HITS** — *offset corruption, weaponized.* The Hex Splicer's product: bytes +fetched from the middle of a frame instead of its start code. Unstable prisms that +detonate into macroblock shrapnel and color inversion if belted too far. Ship fast. +`ASSET (3D): angular unstable prism crackling with inverted-color lightning, half its faces showing a scrambled image, hazard-orange containment frame straining` + +**THE MEGAGLITCH** *(victory product)* — see §7. + +--- + +## 4. MACHINES + +**SEAM EXTRACTOR** — *the miner.* A drill-head that chews mdat seams and spits raw ore. +Era-skinned per stratum (film-reel drill in the Reel Beds, etc.). +`ASSET (3D): industrial mining drill with a CRT monitor for a head, drill bit made of stacked play-button triangles, cable dreadlocks, grimy yellow chassis` + +**DEMUXER** — *the first splitter.* Cleaves raw ore into luma / chroma / audio / MV-flux +output lanes. Literally a machine with one input belt and four differently-glowing +output belts. `ASSET (3D): squat sorting machine with one big intake hopper and four labeled output chutes glowing white, magenta, green, cyan` + +**DEMOSAICER** — *makes color from checkerboard grit.* Interpolation looms weave RGGB +gravel into full-color plates. Parameter dial selects algorithm (AMaZE/LMMSE/VNG4 as +absurd brand names on the faceplate). Feed it stripes → it jams and extrudes MOIRÉ. +`ASSET (3D): loom-like machine threading red green blue gravel into a smooth color sheet, weaving arms mid-motion, big algorithm selector dial with baroque labels` + +**DCT PRESS** — *spatial → frequency.* A hydraulic press whose platen is engraved with +the 8×8 DCT basis-function grid; slams pixel blocks into coefficient card decks. Bigger +era-tier presses (16×16, 64×64, 128×128) are progressively more cathedral-like. +`ASSET (3D): heavy hydraulic press, platen engraved with the iconic grid of cosine-wave basis patterns, glowing card deck sliding out of the output slot` + +**QUANTIZER** — *the crusher, the moneymaker, the sin.* Adjustable jaw that rounds +coefficients to zero. Its single dial (Q) is the most important lever in the factory: +right = more BANDWIDTH + more HF DUST + uglier products. The dial goes to "CRIME". +`ASSET (3D): brutal jaw-crusher with an oversized rotary dial labeled with a smiley face at one end and a skull at the other, glitter dust leaking from its seams` + +**SUBSAMPLER** — *chroma concentrator.* Centrifuge that spins 4:4:4 slurry down to +4:2:2 / 4:1:1 / 4:2:0 grades, venting bandwidth. Leaks by design; place downwind. +`ASSET (3D): centrifuge tank with three grade taps, iridescent stains streaking down its flank, ventilation stack emitting faint rainbow vapor` + +**MV EXTRACTOR & P-CASTER** — *optical-flow refinery.* Watches decoded footage with an +array of eye-cameras and pipes off MV-FLUX; the paired caster prints delta wafers. +`ASSET (3D): machine studded with dozens of small camera lenses all tracking subtly, cyan fluid pipe exiting the back, wafer printer sidecar` + +**GOP ASSEMBLER** — *the packer.* Robotic arm slots 1 anchor slab + N wafers into +crates following a cadence template (editable: IPP, IBBP, I-only…). Cadence templates +are themselves unlockable items. +`ASSET (3D): packing station with robot arm mid-slot, crate on rollers, cadence template punch-cards racked on the wall` + +**MOSH REACTOR** — *tier-1 corruption core.* A decoder run in a sealed vessel and +deliberately starved of anchors: crates go in, the I-frame is winched OUT through a +side airlock (recoverable — sell it!), and the hallucinating decoder extrudes MELT. +`ASSET (3D): pressure reactor with a porthole showing swirling rainbow smear, side airlock cradling a stolen glowing slab, warning placard of a melting face` + +**BLOOM LOOP** — *not a machine — a belt topology.* Any closed belt circle with a +P-FRAME DUPLICATOR on it. Contents compound each lap; tap the loop to draw off graded +bloom. Runaway loops (grade >5) burst and flood the sector with directional smear. +`ASSET (3D, belt piece + duplicator): conveyor segment whose cargo visibly doubles and feathers as it passes a stamping duplicator arch, escalating glow per lap` + +**FIELD LOOM (INTERLACER/DEINTERLACER)** — *weaves and unweaves time.* Splits frames +into odd/even field splinters captured a tick apart, or (run in reverse) weaves them +back — imperfectly, unless fed a motion-adaptive coprocessor module. +`ASSET (3D): weaving loom threading two horizontal slat-sets together into one sheet, teeth slightly misaligned, phosphor green worklight` + +**TELECINE PULLER** — *the 3:2 judder mill.* Cranks 24fps film stock into 30fps product +by duplicating fields on a lumpy cam (see JUDDER CAMS). Runs backwards as an IVTC +purifier — one of the few machines The Correction also uses, awkwardly. +`ASSET (3D): film-projector-meets-gearbox, visible uneven cam linkage, two film paths in and out with mismatched sprocket rhythms` + +**HEX SPLICER** — *endgame chaos lathe.* A robotic hex-editor that nudges stco offsets +by a few bytes so downstream decoders fetch garbage. Produces EXPLOSIVE HITS. Requires +CONTAINER PACK research and a steady buffer feed or it splices *itself*. +`ASSET (3D): surgical robot arm poised over a scrolling hexadecimal ticker-tape, one byte pair held glowing in its tweezers, containment glass, red interior light` + +**DECODE ASIC** *(power gen)* — *cool, efficient, inflexible.* Handles standard profiles +only. `ASSET (3D): server-blade monolith with a huge heatsink afro and a serene LED face` +**SOFTWARE DECODER** *(burst gen)* — *decodes ANYTHING, at any temperature.* Doubles +throughput on demand; generates HEAT; throttles theatrically (fan scream, tick-rate +halving). `ASSET (3D): overclocked tower PC held together with zip ties and prayer, case open, fans glowing hot-red, thermal haze` + +**BUFFER TANK** — see BUFFER CHARGE. **MUXER** — see §7 (it's the rocket). + +--- + +## 5. HAZARDS, WILDLIFE & THE ENEMY + +### Wildlife (ambient, farmable) + +**MOSQUITO SWARMS** — *quantization noise, alive.* Shimmer-gnat clouds that hatch from +HF DUST piles and cluster around any sharp edge in your factory (signage, fresh luma, +the player). Degrade machine precision. Catchable in edge-baited traps → sellable as an +artifact ingredient. The doc's "shimmering swarm around outlines," literalized. +`ASSET (VFX + 3D trap): particle cloud of tiny flickering pixel-gnats; trap is a bug-zapper shaped like a high-contrast black-white edge target` + +**GIBBS WRAITHS** — *ringing, ambulatory.* Ghostly figures made of concentric echo +halos that spawn where contrast is extreme. Harmless but they *duplicate your outline* +and follow you, slightly out of phase. Density = a readable "over-sharpening" warning. +`ASSET (3D character, rigged): translucent humanoid made of nested outline rings, no fill, constantly oscillating between two positions` + +**MOIRÉ BLOOM** — *crystal maze growth.* Spreads across floors wherever repeating +textures face each other. Harvest young = product; let it mature = your factory now has +corridors you didn't design. Some players will farm it as free walls. + +### System hazards + +**BROWNOUT (BUFFER UNDERRUN)** — a drained buffer freezes its whole power domain in a +stuttering last-frame loop while the audio bus emits catastrophic pop-crackle. Machines +resume with a lurch and 1 tick of scrambled output (free chaos, occasionally useful). +**THERMAL SCRAM** — overheated software decoders halve the local tick rate; the *game +itself* visibly drops frames in that sector. The lag IS the damage model. +**BLEED FLOODS** — slurry spills tint every product crossing them until mopped. + +### THE CORRECTION (the enemy faction) + +The immune system of the Bitstream. It does not hate you; it *cannot perceive* you — +only deviation, which it repairs. Escalation ladder: + +1. **PARITY MITES** — beetle-drones that patrol belts and quietly *fix* artifacts back + into clean product (your melt becomes... footage of a lake). Early nuisance. + `ASSET (3D, rigged): rounded beetle drone, hospital-white shell, tiny green checkmark eye, solder-iron proboscis, unsettlingly gentle` +2. **CHECKSUM WARDENS** — heavier units that audit a machine, roll back its last N + outputs, and stamp it with a compliance seal (disabled until you pry the seal off). + `ASSET (3D, rigged): tall white filing-cabinet golem, drawer-chest full of hashes, rubber-stamp fist, red LED ledger eyes` +3. **REDUNDANCY GUNSHIPS** — airborne RAID arrays that *mirror* a sector of your + factory: a clean parallel copy materializes alongside and tries to out-ship you to + THE SCREEN. Your own layout, sanitized, weaponized. Kill the parity link to pop it. + `ASSET (3D): hovering white chassis of five mirrored disk-platter rotors in a row, projecting a ghostly duplicate landscape beneath itself` +4. **HASH AUDITORS** (endgame, from the Fortress) — DCP inquisitors. One byte of + deviation in their scan radius and they refuse — not attack, *refuse* — locking + regions into unplayable 0:00 stasis until you break the lock (see moov heists, §6). + `ASSET (3D, rigged): faceless white-marble cinema usher, flashlight that projects an XML scroll, padlock icon halo, moves only between frames` + +--- + +## 6. RESEARCH, COMMISSIONS & SIDE LOOPS + +**TECH TREE = MEDIA ARCHAEOLOGY.** You research *downward* (excavating older strata for +analog secrets) and *upward* (deriving newer codecs). Era multipliers use the real +efficiency history: MPEG-2 → H.264 ≈ ×2 compression, → HEVC ×1.5, → AV1 ×1.3, each era +also unlocking bigger DCT presses (8×8 → 128×128) and new cadence templates. + +**PRESTIGE = REMASTER.** Reset the file, keep knowledge ("muscle memory of the codec"), +re-encode the world one generation newer. Generation loss is the prestige *bonus* here — +each remaster starts with era-appropriate ambient artifacts already seeded in the soil. + +**COMMISSIONS** arrive by fax (the fax machine is sacred, do not ask why it works). +Absurd recipe orders from unseen glitch-art collectors, e.g.: +- *"1 MELTED ANCHOR SLAB + 3 MOSQUITO SWARMS (live) + 40 bbl CHROMA SLURRY (4:2:0) = 1 VAPORWAVE SUNSET. Deliver before the beat drops."* +- *"600 MACROBLOCK BRICKS, sky-blue, MISLABELED REC2020. Purpose: none of your business."* +- *"One (1) GIBBS WRAITH, willingly."* + +**MOOV HEISTS** (side mode, feeds the campaign): Hash Auditors lock a region → you +infiltrate its container, scan scrolling hex for real frame signatures (AAC `0xFFF` +sync words, H.264 NAL start codes), and rebuild/forge the stco/stsz index to your +advantage. Papers-Please-meets-defrag; the minigame from GLYTCH's REPAIR mode, reused. + +**AUDIO WING** (optional expansion): PCM ingots, sample-rate drift (44.1k product on a +48k line slowly desyncs the *whole factory's* rhythm), and the asymmetric sync scoring +rule — audio may lag ≤120ms, but audio that *leads* by even a few ms triggers instant +commission rejection. The pickiest customers are evolutionary. + +--- + +## 7. THE ENDGAME: THE FORTRESS & THE MEGAGLITCH + +**THE MUXER** is your rocket: a launch-gantry that assembles a complete container — +ftyp seal, mdat payload masses, and the hand-built **moov brain** (stsz ledger + stco +map + stts metronome + stss keyring, each its own late-game production line) — and +ships the finished file to THE SCREEN as one colossal composited corruption: the +**MEGAGLITCH**. Victory plays your actual factory's shipping history as a rendered +video. (Real-render tie-in: the layout compiles to an ffmpeg/PYXLFK graph — belts are +`filter_complex`; the save file is a render-farm job for the Mac fleet.) +`ASSET (3D, hero structure): launch gantry embracing a monolithic container rocket built of nested translucent boxes, innermost box a glowing brain of index tape-reels, umbilical belts feeding it from every direction` + +**THE FORTRESS (DCP)** is the final biome and the game's thesis-statement difficulty +cliff: inside its walls *your entire verb set fails*. JPEG 2000 wavelet masonry — no +blocks, no seams to mosh. Every frame intra-coded — no dependency chains to starve. No +motion vectors *at all*. PCM audio too pure to pop. AES-CBC gates, KDM time-locks that +only open during scheduled showings, and hash sentries with zero-tolerance policy. +You cannot corrupt The Fortress. The twist: **you don't have to.** Its own perfection +is the exploit — flip one byte and it *refuses to play itself*. The final act inverts +your win condition from "make it glitch" to "make it silent," or steal the KDM window. +`ASSET (environment kit): blinding white cathedral of smooth waveleted curves, zero right angles, XML scripture friezes, spotlight-usher sentries, one hairline black crack (scripted)` + +--- + +## 8. VISUAL STYLE GUIDE (for every MODELBEAST batch) + +- **Two-material rule:** every asset = grimy industrial body (rust, gaffer tape, hazard + stripes, zip ties) + exactly ONE impossible element (CRT glow, iridescent fluid, + interference sheen, embedded image). The impossible element is the silhouette's focus. +- **Palette:** base world in desaturated industrial neutrals; ALL saturation belongs to + media/artifacts (chroma slurry, gamut paints, THE SCREEN). Color = value = literally + the resource. The world gets more colorful only where the player has made a mess. +- **Era skins:** Reel Beds = sepia/brass/celluloid; Broadcast = phosphor green + wood- + grain TV; Disc = rainbow-on-black gloss; Stream = flat white plastic + LED; Fortress + = blinding matte white. The Correction is always hospital-white with green checkmarks. +- **Animation motif:** clean things move at 60fps; corrupted things move *wrong on + purpose* — 3:2 judder for film-era, 2-frame loops for analog, held-then-lurch for + buffer trouble. Wrongness of motion is a faction uniform. +- **UI voice:** OSHA-poster deadpan. Everything horrifying is labeled like routine + industrial equipment. + +## 9. MODELBEAST PRODUCTION NOTES + +- Host: `MB_HOST=http://100.89.131.57:8777` (m3ultra, tailnet). Headless via `mb` CLI; + ops brief in `~/Documents/modelbeast/AGENTS.md` on that machine. +- Pipeline per 3D asset: concept image → `sf3d` (local, fast) for props; `fal_trellis2` + (paid, higher fidelity) reserved for hero assets (Muxer, Mosh Reactor, Fortress kit) + — check the canon cache before any paid generation (asset-pipeline house rule). +- Characters/creatures that need rigs (Gibbs Wraith, Parity Mite, Wardens, Auditor): + route through the character_kit fleet rule — generate the mesh, then bind to the + shared clip banks; bespoke motion (the Auditor's between-frames teleport, Mite repair + loop) is hand-authored, not Mixamo-searched. +- Belts/pipes/tiles are kit-bashed modular pieces: generate 3–4 segment variants each, + keep polycounts belt-friendly; VFX-heavy entries (melt, static, heat) are shaders, + not meshes — the ASSET prompt is the *reference image* prompt for the shader artist + (also you). +- Every asset generated gets its element's codex name — this file is the manifest; + check off against it. diff --git a/fktry/CONTRACTS.md b/fktry/CONTRACTS.md new file mode 100644 index 0000000..bd70ac9 --- /dev/null +++ b/fktry/CONTRACTS.md @@ -0,0 +1,57 @@ +# CONTRACTS — how the lanes fit together (ORCHESTRATOR-OWNED) + +The binding type definitions live in [`src/contracts.ts`](src/contracts.ts) — that file +is the law. This doc explains the shape of the machine in prose. + +## Data flow + +``` +data/*.json ──▶ main.ts loads GameData + │ + ┌───────────┼─────────────────────────┐ + ▼ ▼ ▼ + sim.init() renderer.init() ui.init() / screen.init() + │ + 30 tps fixed timestep: sim.tick() + │ + ├─▶ sim.snapshot() ──▶ renderer.render(snap, alpha) (every rAF) + │ ──▶ ui.update(snap, events) + └─▶ sim.drainEvents() ─▶ screen.onEvents(events) + + user input: UI builds Commands ─▶ bus.dispatch ─▶ sim.enqueue + renderer supplies pickTile + ghost preview +``` + +## Ownership map + +| Path | Owner | Everyone else | +|---|---|---| +| `src/contracts.ts`, `src/main.ts`, root config, this doc, `MASTERPLAN.md` | orchestrator | read-only | +| `src/sim/**` | LANE-SIM | read-only | +| `src/render/**`, `public/assets/**` (consumption) | LANE-RENDER | read-only | +| `src/ui/**` | LANE-UI | read-only | +| `src/screen/**` | LANE-SCREEN | read-only | +| `data/**` | LANE-DATA | read-only | +| `lanes/LANE-X.md` NOTES section | lane X | orchestrator writes ORDERS section | +| `../docs/FKTRY_LORE.md` | canon | read-only for all lanes | + +## Key invariants + +- **Snapshot is read-only.** Renderer/UI/Screen never mutate it. Sim may reuse + internal buffers between snapshots; consumers must not hold references across frames. +- **All mutation goes through Commands.** No lane reaches into sim internals. +- **Events are drained once per frame by main.ts** and fanned out; consumers get the + same array — treat it as immutable. +- **IDs are data-driven.** Renderer/UI/Screen never hard-code item/machine ids; they + key off `GameData` and the `asset` field. New content should light up with zero code. +- **`alpha`** in `renderer.render(snap, alpha)` is the 0..1 fraction between the last + sim tick and the next — use it to interpolate belt item positions for smooth motion. +- **Belt visual speed** derives from `MachineDef.beltSpeed` and `BeltItem.t`; sim owns + the truth, renderer owns the smoothness. +- **Coordinates**: tile grid, origin at world center, +x east, +y south. `Dir` 0..3 = + N,E,S,W clockwise. Machine `pos` = origin corner (min x, min y of footprint). + +## Contract-change requests + +Written in your lane NOTES as `CONTRACT REQUEST: `. The orchestrator +batches them between rounds. Until granted, work around locally inside your lane. diff --git a/fktry/MASTERPLAN.md b/fktry/MASTERPLAN.md new file mode 100644 index 0000000..836b36f --- /dev/null +++ b/fktry/MASTERPLAN.md @@ -0,0 +1,74 @@ +# FKTRY MASTERPLAN — orchestration doc + +**Read this first, every round, whoever you are.** + +FKTRY is a Factorio-style glitch-production factory game set inside a dying video file. +The full world bible is [`../docs/FKTRY_LORE.md`](../docs/FKTRY_LORE.md) — machines, +resources, enemies, eras, and the visual style guide all live there. Read it once, +fully, before your first round. It is canon; when in doubt about tone or naming, the +codex wins. + +## Cast + +- **ORCHESTRATOR** (Fable session with John): owns this file, `CONTRACTS.md`, + `src/contracts.ts`, `src/main.ts`, and the CURRENT ORDERS section of every lane doc. + Reviews each round, writes the next round's orders. +- **FIVE LANES** (Opus 4.8 executor sessions, run in parallel): SIM, RENDER, UI, + SCREEN, DATA. Each lane has a doc in `lanes/` and an exclusive set of owned paths. +- **MODELBEAST** (asset factory on the m3ultra): generated GLB/sprite assets arrive + asynchronously into `public/assets/` — LANE-RENDER hot-swaps them in, nobody waits + for them. + +## The round protocol (every lane, every round) + +1. `git pull` first. Read YOUR lane doc (`lanes/LANE-.md`): the **CURRENT ORDERS** + section is your task list for this round. Read `CONTRACTS.md` + `src/contracts.ts`. +2. Do the work. Stay inside your **owned paths** (listed in your lane doc). You may + READ anything in the repo; you WRITE only in your lane. +3. Verify before reporting — all three, every round: + - `npm run check` (tsc clean) + - `npm test` (all green; SIM lane especially) + - `npm run dev` → open http://localhost:8150 → confirm the app boots and YOUR + surface behaves; check the browser console for errors. "Should work" ≠ verified. +4. Append a round entry to the **NOTES** section at the bottom of your lane doc + (template is there). Be honest: broken/unfinished things get written down, not + hidden. Questions and contract-change requests go here too — the orchestrator + reads every note. +5. Commit with your lane prefix: `[sim] belt merge logic + tests`. One or a few + focused commits, not one mega-commit. Push. + +## Hard rules + +- **Never edit**: `MASTERPLAN.md`, `CONTRACTS.md`, `src/contracts.ts`, `src/main.ts`, + root config (`package.json`, `tsconfig.json`, `index.html`), other lanes' paths, + other lanes' docs. Need a dependency added or a contract changed? Write it in NOTES + with rationale; the orchestrator handles it next round. +- **Never redesign the architecture.** You are an executor on a lane. Brilliant ideas + belong in NOTES ("PROPOSAL:"), not in the diff. +- **Determinism (SIM)**: no `Date.now()`, no unseeded `Math.random()` inside the sim. + Same seed + same command sequence = identical state, forever. Everything else may be + as flashy as it likes. +- **Placeholders are honorable.** Do not block on assets, other lanes' features, or + missing data. Build to the contract, stub the rest, note the stub. +- If the app won't boot because of someone else's in-flight work, note it, build + against the contracts anyway, and verify with `npm test`/`check` this round. + +## Milestones (orchestrator's map — lanes don't self-assign ahead) + +- **M1 — FLOW** (rounds 1-2): place extractor → belts → demuxer → quantizer → mosh + reactor → shipper; items visibly ride belts; MELT ships; THE SCREEN corrupts in + response. The whole fantasy in miniature. +- **M2 — PRESSURE**: bandwidth economy + brownouts, heat/throttling, HF dust piles, + first wildlife (mosquito swarms), commissions via fax UI. +- **M3 — DEPTH**: tech tree + eras, bloom loops, subsampler bleed, moiré growth, + save/load, The Correction (parity mites). +- **M4 — AWESOME**: megaglitch muxer, strata/biomes, remaster prestige, audio, + The Fortress. Real MODELBEAST assets throughout. + +## Orchestrator review checklist (per round) + +Pull, read all five NOTES entries, then: `npm run check && npm test`, play the build, +diff each lane against its owned paths (ownership violations get reverted), verify +claimed features actually work, reconcile cross-lane questions, update CONTRACTS if +(and only if) two lanes need it, write next CURRENT ORDERS in each lane doc, commit +`[orchestrator] round N orders`. diff --git a/fktry/data/commissions.json b/fktry/data/commissions.json new file mode 100644 index 0000000..0020b79 --- /dev/null +++ b/fktry/data/commissions.json @@ -0,0 +1,4 @@ +[ + { "id": "first-taste", "flavor": "One (1) unit of MELT. We hear you make it fresh. No questions will be answered.", + "wants": { "melt": 1 }, "rewardBandwidth": 50 } +] diff --git a/fktry/data/items.json b/fktry/data/items.json new file mode 100644 index 0000000..2a8e803 --- /dev/null +++ b/fktry/data/items.json @@ -0,0 +1,11 @@ +[ + { "id": "mdat-ore", "name": "MDAT ORE", "codex": "2:mdat-ore", "tier": 0, "color": "#1a1a22" }, + { "id": "luma-bars", "name": "LUMA BARS", "codex": "2:luma-bars", "tier": 1, "color": "#c0c0c0" }, + { "id": "chroma-slurry", "name": "CHROMA SLURRY", "codex": "2:chroma-slurry", "tier": 1, "color": "#ff3fd4" }, + { "id": "coefficient-pack", "name": "COEFFICIENT PACK", "codex": "2:coefficient-packs", "tier": 1, "color": "#3fffe0" }, + { "id": "hf-dust", "name": "HF DUST", "codex": "2:hf-dust", "tier": 1, "color": "#e8e0ff" }, + { "id": "anchor-slab", "name": "I-FRAME (ANCHOR SLAB)", "codex": "2:i-frame", "tier": 1, "color": "#fff2a0" }, + { "id": "delta-wafer", "name": "P-FRAME (DELTA WAFER)", "codex": "2:p-frame", "tier": 1, "color": "#7fb0ff" }, + { "id": "gop-crate", "name": "GOP CRATE", "codex": "2:gop-crate", "tier": 1, "color": "#a07840" }, + { "id": "melt", "name": "MELT", "codex": "3:melt", "tier": 2, "color": "#ff7a3f" } +] diff --git a/fktry/data/machines.json b/fktry/data/machines.json new file mode 100644 index 0000000..4bc2794 --- /dev/null +++ b/fktry/data/machines.json @@ -0,0 +1,16 @@ +[ + { "id": "seam-extractor", "name": "SEAM EXTRACTOR", "codex": "4:seam-extractor", "kind": "extractor", + "footprint": { "x": 2, "y": 2 }, "recipes": ["extract-mdat"], "powerDraw": 2, "asset": "seam-extractor" }, + { "id": "belt", "name": "STREAM BELT", "codex": "4:belts", "kind": "belt", + "footprint": { "x": 1, "y": 1 }, "recipes": [], "powerDraw": 0, "beltSpeed": 2, "asset": "belt" }, + { "id": "demuxer", "name": "DEMUXER", "codex": "4:demuxer", "kind": "crafter", + "footprint": { "x": 2, "y": 2 }, "recipes": ["demux-ore"], "powerDraw": 3, "asset": "demuxer" }, + { "id": "quantizer", "name": "QUANTIZER", "codex": "4:quantizer", "kind": "crafter", + "footprint": { "x": 2, "y": 2 }, "recipes": ["quantize"], "powerDraw": 4, "asset": "quantizer" }, + { "id": "mosh-reactor", "name": "MOSH REACTOR", "codex": "4:mosh-reactor", "kind": "crafter", + "footprint": { "x": 3, "y": 3 }, "recipes": ["mosh"], "powerDraw": 8, "asset": "mosh-reactor" }, + { "id": "decode-asic", "name": "DECODE ASIC", "codex": "4:decode-asic", "kind": "power", + "footprint": { "x": 2, "y": 2 }, "recipes": [], "powerDraw": 0, "powerGen": 20, "asset": "decode-asic" }, + { "id": "shipper", "name": "SCREEN UPLINK", "codex": "7:the-muxer", "kind": "shipper", + "footprint": { "x": 2, "y": 2 }, "recipes": [], "powerDraw": 5, "asset": "shipper" } +] diff --git a/fktry/data/recipes.json b/fktry/data/recipes.json new file mode 100644 index 0000000..60f0c6c --- /dev/null +++ b/fktry/data/recipes.json @@ -0,0 +1,6 @@ +[ + { "id": "extract-mdat", "machine": "seam-extractor", "inputs": {}, "outputs": { "mdat-ore": 1 }, "ticks": 30, "bandwidth": 2 }, + { "id": "demux-ore", "machine": "demuxer", "inputs": { "mdat-ore": 2 }, "outputs": { "luma-bars": 1, "chroma-slurry": 1 }, "ticks": 45, "bandwidth": 3 }, + { "id": "quantize", "machine": "quantizer", "inputs": { "luma-bars": 1 }, "outputs": { "coefficient-pack": 1, "hf-dust": 1 }, "ticks": 30, "bandwidth": -6 }, + { "id": "mosh", "machine": "mosh-reactor", "inputs": { "coefficient-pack": 2, "chroma-slurry": 1 }, "outputs": { "melt": 1, "anchor-slab": 1 }, "ticks": 90, "bandwidth": 10 } +] diff --git a/fktry/data/tech.json b/fktry/data/tech.json new file mode 100644 index 0000000..fe51488 --- /dev/null +++ b/fktry/data/tech.json @@ -0,0 +1 @@ +[] diff --git a/fktry/index.html b/fktry/index.html new file mode 100644 index 0000000..2901f7b --- /dev/null +++ b/fktry/index.html @@ -0,0 +1,22 @@ + + + + + WIMVEE FKTRY + + + + +
+ +
+ + + diff --git a/fktry/lanes/LANE-DATA.md b/fktry/lanes/LANE-DATA.md new file mode 100644 index 0000000..cdcdf4e --- /dev/null +++ b/fktry/lanes/LANE-DATA.md @@ -0,0 +1,71 @@ +# LANE-DATA — content, recipes, balance, and canon-keeping + +You are an Opus 4.8 executor on the DATA lane of FKTRY. Read `../MASTERPLAN.md` and +`../CONTRACTS.md` first. Your bible is `../../docs/FKTRY_LORE.md` — you are its +transcriber into machine-readable canon. When the codex and convenience disagree, the +codex wins; when the codex is silent, invent IN ITS VOICE and note what you invented. + +**Mission:** every item, machine, recipe, tech, and commission as clean JSON, plus the +validator that keeps five parallel lanes from drowning in dangling ids. Content should +light up in-game with zero code changes from other lanes. + +**Owned paths:** `data/**`, `src/sim/data-validate.test.ts` — EXCEPTION: this one test +file in sim's directory is yours; it validates data, not sim. Nothing else in +`src/sim/`. +**Never touch:** contracts, main.ts, other lanes' code. Schema changes are CONTRACT +REQUESTs. + +**Standing rules (all rounds):** +- Ids: kebab-case matching codex names (`chroma-slurry`, `mosh-reactor`). `codex` + field points at the lore doc section (`"3:melt"` = §3, MELT entry). +- Balance philosophy: absurd flavor, honest math. Ratios should create real routing + pressure (byproducts you must deal with, not vent). Steal shamelessly from the + doc's real numbers (era efficiency multipliers, 4:2:0 = half the chroma, GOP + cadences). +- Never delete an id other lanes may reference mid-round — deprecate in NOTES first. + +--- + +## CURRENT ORDERS — Round 1 (goal: milestone M1 "FLOW" + M2 prep) + +The seed JSONs in `data/` are orchestrator placeholders — correct them, then grow: + +1. **Validator first** (`src/sim/data-validate.test.ts`, vitest): every recipe's + machine + items exist; every machine's recipes exist and point back at it; every + tech unlock exists; commission wants exist; ids unique + kebab-case; colors valid + hex; footprints ≥1×1. This test is the lane's handshake — it must fail loudly on + any dangling reference. +2. **Items** → full §2 + §3 catalog: all raw resources, refined intermediates, frames, + the five science packs, and tier-2 products (melt, bloom-concentrate, + macroblock-bricks, ringing-halos, static-canister, moire-crystal, false-color- + speckle, judder-cams, explosive-hits, gamut paints ×3). Colors from codex vibes. +3. **Machines** → full §4 catalog (demosaicer, dct-press, subsampler, mv-extractor, + p-caster, gop-assembler, bloom-duplicator, field-loom, telecine-puller, + hex-splicer, software-decoder, buffer-tank...). Machines beyond M1's seven should + exist in data even though sim/render only generically support crafter/power kinds + — that's fine, they'll work as generic crafters until given bespoke mechanics. +4. **Recipes** → wire the economy: ore → luma/chroma/mv-flux (demux), luma → coeff + packs + hf-dust (quantize, generates bandwidth), mv-flux → delta-wafers, slab + + wafers → gop-crate, gop-crate → melt + reclaimed slab (mosh), coeff overdrive → + macroblock-bricks + double hf-dust, hf-dust → static-canister, science pack + assembly ×3 (analog/spatial/temporal). Include at least two genuinely absurd + ratios for comedy that still balance. +5. **Tech tree v1** → `disc` and `stream` era nodes: unlock quantizer tiers, mosh + reactor, bloom duplicator, subsampler grades. Costs in science packs. +6. **Commissions** → 8-10 in full fax voice (§6 has three exemplars). Escalating + absurdity and quantity; at least one demanding a *live* hazard product you know + isn't shippable yet (mark it `"wants": {"mosquito-swarm": 3}` — forward canon; + the validator should allow items that exist in data even if no recipe makes them). + +**Definition of done:** `npm test` green including your validator; dev server still +boots with expanded data (placeholders render for everything); every entry traceable +to a codex section. NOTES list what you invented beyond the codex. + +--- + +## NOTES (append-only log, newest at bottom) + +``` +### Round N — YYYY-MM-DD — [your model] +SHIPPED: / DECISIONS: / INVENTED: / BLOCKED/BROKEN: / CONTRACT REQUEST: / NEXT: +``` diff --git a/fktry/lanes/LANE-RENDER.md b/fktry/lanes/LANE-RENDER.md new file mode 100644 index 0000000..36f55ac --- /dev/null +++ b/fktry/lanes/LANE-RENDER.md @@ -0,0 +1,67 @@ +# LANE-RENDER — three.js world renderer + +You are an Opus 4.8 executor on the RENDER lane of FKTRY. Read `../MASTERPLAN.md` and +`../CONTRACTS.md` first; the world bible + visual style guide (§8) is +`../../docs/FKTRY_LORE.md` — §8 is YOUR section, follow it. + +**Mission:** make the Bitstream visible. Isometric factory view, machines, belts with +smoothly interpolated items, ghosts, selection — and the hot-swap pipeline that lets +MODELBEAST GLB assets land mid-development without a code change. + +**Owned paths:** `src/render/**`, `public/assets/**` (manifest + loading; the files +themselves arrive from MODELBEAST). +**Never touch:** contracts, main.ts, other lanes. Sim is truth: you render snapshots, +you never simulate. If motion looks wrong, interpolate better or note it — don't +"fix" positions locally. + +**Standing rules (all rounds):** +- 60fps with 500 entities + 2,000 belt items on an M-series MacBook. Instanced meshes + for belts/items from day one — you will not get to retrofit this later. +- Placeholder aesthetic is a feature: crisp box-primitive machines tinted per codex + `color`, NOT gray cubes. Two-material rule even for placeholders: dark body + one + emissive accent. +- Every entity mesh keys off `MachineDef.asset` / `ItemDef.id` through the registry — + zero hard-coded ids. + +--- + +## CURRENT ORDERS — Round 1 (goal: milestone M1 "FLOW") + +Replace the stub in `src/render/index.ts`: + +1. **Camera + controls.** Orthographic isometric-style view. Pan: middle-drag or WASD. + Zoom: wheel (clamped ~8..40 world units). Window resize handled. +2. **Ground.** Tile grid over the 64×64 world; subtle Stream-Crust styling (dark + `#0a0812` base, faint `#181425` lines) — see style guide §8. A soft vignette or + fog so the world doesn't just end. +3. **Asset registry + hot-swap.** `registry.ts`: maps asset key → THREE.Object3D + factory. Default: procedural placeholder (footprint-sized beveled box, body color + from data, one emissive accent, tiny idle animation — e.g. quantizer jaw bob). + On init, attempt `GLTFLoader` for `public/assets/models/.glb`; if present it + replaces the placeholder factory. Also poll or re-check on a 10s timer in dev so + assets dropped in mid-session appear without reload (note what you implement). +4. **Entities.** Sync scene to `snap.entities` (add/remove/rotate). Belts get a flat + directional piece with an animated arrow/chevron texture (shader or UV scroll). +5. **Belt items.** InstancedMesh per item type (colored octahedron/box placeholder), + positioned from `BeltItem.t` + belt entity pos/dir, interpolated with `alpha` for + butter-smooth motion at 30 tps sim. +6. **Picking + ghost.** `pickTile` via raycast to the ground plane. `setGhost` shows + the selected machine's placeholder at the hovered tile, tinted cyan; red tint if + tiles occupied (you can read occupancy from `snap.entities` footprints). +7. **Feedback dressing (cheap but load-bearing):** jammed machines get a small + blinking amber light; brownout dims the whole scene ~30% and flickers lights + (listen to snapshot.bandwidth.brownout). + +**Definition of done:** dev server shows the factory; placing a line from the UI (or +console dispatch) shows machines + items gliding down belts smoothly; a GLB dropped +into `public/assets/models/quantizer.glb` replaces the placeholder. `npm run check` +clean. NOTES written. + +--- + +## NOTES (append-only log, newest at bottom) + +``` +### Round N — YYYY-MM-DD — [your model] +SHIPPED: / DECISIONS: / BLOCKED/BROKEN: / CONTRACT REQUEST: / PROPOSAL: / NEXT: +``` diff --git a/fktry/lanes/LANE-SCREEN.md b/fktry/lanes/LANE-SCREEN.md new file mode 100644 index 0000000..2b8d7c0 --- /dev/null +++ b/fktry/lanes/LANE-SCREEN.md @@ -0,0 +1,65 @@ +# LANE-SCREEN — THE SCREEN compositor & glitch shaders + +You are an Opus 4.8 executor on the SCREEN lane of FKTRY. Read `../MASTERPLAN.md` and +`../CONTRACTS.md` first; world bible `../../docs/FKTRY_LORE.md` (§1 THE SCREEN, §3 +products, §8 style). Also read `../../index.html` — the original WIMVEE GLYTCH +prototype — its fragment shader is your seed stock: 8 glitch params (mosh, melt, +chroma, tear, roll, burn, noise, freeze) already written and tuned. + +**Mission:** the payoff object. THE SCREEN is the sky-display everything ships to — +the player's factory output composited live as escalating video corruption. When +someone screenshots this game, they screenshot your canvas. It must start sterile and +end deranged, and every shipped item must visibly matter. + +**Owned paths:** `src/screen/**`. +**Never touch:** contracts, main.ts, other lanes, the GLYTCH prototype (read-only +seed stock — port, don't move). + +**Standing rules (all rounds):** +- WebGL (raw or three.js — your call, note it) on the provided 640×360 canvas. + Budget: <2ms/frame; THE SCREEN is garnish, not the meal. +- Corruption must be *legible*: a player who ships 40 chroma slurry should SEE chroma + damage specifically. Item → artifact mapping is the design core, keep it data-driven + off `ItemDef.id`. +- Base content starts as procedural "clean programming" — sterile SMPTE-ish test + patterns, slow pans, timestamp overlay (port `makeBaseTexture` thinking from the + prototype; animate it subtly so corruption has motion to chew on). + +--- + +## CURRENT ORDERS — Round 1 (goal: milestone M1 "FLOW") + +Replace the stub in `src/screen/index.ts`: + +1. **Port the GLYTCH shader stack** into a proper module (`glitchStack.ts`): vertex + + fragment shader with the 8 uniforms, compiled against your base texture. Keep + param semantics identical to the prototype (it's tuned; respect the tuning). +2. **Corruption ledger.** `onEvents`: each `shipped` event adds to a per-item tally. + Map items → param pressure in `corruptionMap.ts`, e.g. `melt → u_mosh+u_melt`, + `chroma-slurry → u_chroma`, `hf-dust → u_noise`, `anchor-slab → REDUCES overall + corruption slightly` (shipping clean anchors sanitizes — nice tension, note it for + the orchestrator). Unknown items → small generic noise bump. Pressure eases toward + its tally-driven target (lerp) so shipments feel like waves, not switches. +3. **Escalation curve.** Total corruption 0→1 over roughly the first 100 shipped + items (tune by feel), log-ish so early shipments feel huge. Above 0.8, add + compound wobble (params cross-modulate slowly) so a mature factory's SCREEN looks + *alive*, not maxed-out static. +4. **Brownout reaction.** On `brownout:true`, freeze-frame + heavy dropout lines + + desync judder until it lifts. The factory's pain shows in the sky. +5. **Idle charm.** With zero corruption, the clean feed runs bland loops with a + "NOTHING IS WRONG" chyron. First shipment ever interrupts it with a single frame + of full-white glitch — the awakening. Cheap, unforgettable. + +**Definition of done:** dev build — screen starts sterile; console-dispatch a few +shipments (or wait for the real chain) and corruption rises, item-specifically; +brownout visibly seizes it. `npm run check` clean, frame budget respected (note +measured ms). NOTES written. + +--- + +## NOTES (append-only log, newest at bottom) + +``` +### Round N — YYYY-MM-DD — [your model] +SHIPPED: / DECISIONS: / BLOCKED/BROKEN: / CONTRACT REQUEST: / PROPOSAL: / NEXT: +``` diff --git a/fktry/lanes/LANE-SIM.md b/fktry/lanes/LANE-SIM.md new file mode 100644 index 0000000..8e9ae52 --- /dev/null +++ b/fktry/lanes/LANE-SIM.md @@ -0,0 +1,75 @@ +# LANE-SIM — deterministic factory simulation + +You are an Opus 4.8 executor on the SIM lane of FKTRY. Read `../MASTERPLAN.md` and +`../CONTRACTS.md` before anything else; the world bible is `../../docs/FKTRY_LORE.md`. + +**Mission:** the headless, deterministic heart of the game. Grid, entities, belts, +recipes, power, events. If the renderer were deleted, your sim should still be fully +playable through unit tests. You are the lane the other four trust with their lives. + +**Owned paths:** `src/sim/**` (including your tests: `src/sim/*.test.ts`). +**Never touch:** contracts, main.ts, other lanes, data JSONs (request changes via NOTES). + +**Standing rules (all rounds):** +- Deterministic: seedable RNG (write your own mulberry32-style helper), no wall-clock, + no unseeded Math.random. Same seed + same commands = identical snapshots. +- Every mechanic lands with tests. `npm test` green before you write NOTES. +- Performance target: 1,000 entities + 5,000 belt items at 30 tps without heroics. + Prefer flat arrays and index maps over object soup. Don't allocate in the tick loop + when avoidable. +- Snapshot may reuse buffers, but its SHAPE must always match `SimSnapshot`. + +--- + +## CURRENT ORDERS — Round 1 (goal: milestone M1 "FLOW") + +Replace the stub in `src/sim/index.ts` with a real implementation: + +1. **World + placement.** Tile grid (start 64×64, world-centered). `place` command: + validate footprint fits and tiles are free, spawn `EntityState`, emit `placed`. + `remove` (emit `removed`, refund nothing yet), `rotate`, `setPaused`. Invalid + commands are silently dropped (UI will preview validity later). +2. **Belts.** `kind:'belt'` entities carry up to 2 items each as `BeltItem` (t: 0..1), + moving at `beltSpeed` tiles/sec. Items transfer to the belt/machine the belt points + into (dir). Items on a belt keep minimum spacing 0.45. Belt→machine: push into + `inputBuf` if the machine's current recipe wants that item and buffer < 2× recipe + need; otherwise the item waits (belt backs up — this is core Factorio feel, get it + right). Machine→belt: outputs pop onto an adjacent belt facing away, one item per + available slot. +3. **Crafting.** Machines with recipes: when `inputBuf` covers `inputs`, consume, + run `ticks` (progress 0..1), emit `crafted`, deposit `outputs` into `outputBuf`. + If `outputBuf` holds ≥ 4× outputs, machine stalls with `jammed:"output full"` + (emit `jammed` once per stall, not per tick). Extractors need no inputs. Machines + with multiple recipes use `setRecipe`; default to `recipes[0]`. +4. **Bandwidth (power) v1.** Sum powerGen (power kind) vs powerDraw of all entities + + active recipe `bandwidth` (note: negative recipe bandwidth GENERATES — quantizer + compression pays power, per lore). If draw > gen: global speed multiplier = + gen/draw for all progress and belt movement (brownout), emit `brownout` on/off + edges, set `snapshot.bandwidth` accordingly. No storage/buffer tanks yet. +5. **Shipping.** `kind:'shipper'` consumes ANY item arriving in its input, increments + `shippedTotal`, emits `shipped`. Track the single active commission (first in + data): fill `commissionProgress`, emit `commissionDone` once satisfied. +6. **Tests** (minimum): placement collision; belt line moves an item end to end in + the expected tick count; belt back-pressure (full line stops cleanly, no item + loss/dupe); demux recipe consumes 2 ore → 1 luma + 1 slurry; brownout halves + speed at draw=2×gen; determinism (two sims, same seed+commands, 500 ticks, + deep-equal snapshots); shipping increments and fires commissionDone. + +**Definition of done:** with the dev server running, the orchestrator can (via UI or +console `__fktryBus.dispatch(...)`) place extractor→belts→demuxer→quantizer→ +mosh-reactor→shipper and watch `shippedTotal.melt` climb. All tests green. NOTES +written (decisions, gotchas, what you'd tackle in round 2). + +--- + +## NOTES (append-only log, newest at bottom — template below) + +``` +### Round N — YYYY-MM-DD — [your model] +SHIPPED: what actually works now (verified how) +DECISIONS: choices you made inside your mandate +BLOCKED/BROKEN: anything not working, honestly +CONTRACT REQUEST: (if any) +PROPOSAL: (ideas for the orchestrator, optional) +NEXT: what you'd do next round if asked +``` diff --git a/fktry/lanes/LANE-UI.md b/fktry/lanes/LANE-UI.md new file mode 100644 index 0000000..0c31e02 --- /dev/null +++ b/fktry/lanes/LANE-UI.md @@ -0,0 +1,65 @@ +# LANE-UI — HUD, build tools, and the voice of the game + +You are an Opus 4.8 executor on the UI lane of FKTRY. Read `../MASTERPLAN.md` and +`../CONTRACTS.md` first; the world bible is `../../docs/FKTRY_LORE.md`. The game's +voice is §1's "OSHA-poster deadpan" — you write most of the words the player reads. +Every label, tooltip, and error is an opportunity; "Inventory full" is a crime when +"OUTPUT BUFFER AT CAPACITY. THIS IS A YOU PROBLEM." is available. + +**Mission:** everything DOM. Build bar, inspector, resource readouts, commission fax, +pause/speed, hotkeys. Plain TypeScript + DOM — no framework, no CSS libs. + +**Owned paths:** `src/ui/**` (styles included — inject a ` + + +

WIMVEE GLYTCH

+
+ ROUND 1 + SYNC 00.0% + +
+
+
TARGET SIGNAL
+
YOUR SIGNAL
+
+
    +
    + ←/→ or L1/R1: select property · ↑/↓ or d-pad: adjust · left stick Y: fine adjust · + hold shift / R2: slow · N or START: new round · match the target signal to ≥96% sync +
    + + + +