Commit Graph

66 Commits

Author SHA1 Message Date
m3ultra
d6aa124cb7 Log Sprint 2 landing: decisions 3 & 5, rain occlusion, fog fix
Includes the controlled downdraft rebalance table for Lane B, the frozen
debris.pieces seam, and the garden-HP design question for Lane A (rain shadow
vs sun coverage).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-17 00:12:03 +10:00
m3ultra
264c2e25d2 Lane D: solids collision, the M3 verbs, shelter and stumble
At gate 1 the ped walked straight through the house. Collision now stops it
0.30 m off the wall face (expected -9.70, measured -9.70), off trunks, posts and
the fence, and slides along a wall hit at an angle. Injected as opts.collide the
way groundAt already was, so player.sim.js stays zero-import and node-runnable.

Two things the real yard taught, neither guessable from the plan:
- `fence` is a GROUP of 37 child meshes whose combined box is the entire 30x20 m
  yard, so one box per solids entry is useless. Flattened to 43 leaf boxes.
- the house ROOF spans y 2.99-3.21 and reaches 0.4 m FURTHER into the yard than
  the wall under it (eaves overhang). A flat footprint test would stop a 1.7 m
  person dead at an invisible eave, so every box is filtered by vertical overlap
  with the body and the roof drops out on its own.
Boxes are built once (solids are static) and distance-pruned — no per-frame
raycast, which is the thing Lane A measured as catastrophic on the terrain.

The M3 pack is wired: carrying swaps locomotion to Carry/CarryIdle; an
interaction names its own verb through a new `clip` field on the interact spec
(Crank at a turnbuckle, PickUp at the shed table); StumbleBack fires on a gust
that breaks your stride but can't floor you — below knockWind on purpose, so a
storm reads as shoved → stumbling → floored rather than fine-fine-fine-flat.

TakeCover (hold C) became a real mechanic rather than a pose: brace and knockWind
x2.0, shove x0.25. A 38 m/s gale floors you standing and doesn't while braced;
let go in the same gale and you're down in half a second. It raises the bar, it
does not remove it — a big enough gust still wins, braced or not. So the storm's
answer to "the gusts are too strong to cross the yard" is now wait one out and
move in the lull, which is the repair-window language DESIGN.md already uses.

wireYardActions now reads sailRig.corners[i] live by index instead of capturing
the corner object — per Lane A's warning that attach() replaces the array, a
captured corner is one the sim no longer steps and would gate forever on a
`broken` flag that can never change again.

35 Lane D asserts, 0 fail (was 20). Carry/shelter/knockdown verified against the
real 17-clip pack in the assembled game, not only in the harness.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-17 00:08:46 +10:00
m3ultra
de86aa1662 Post gate 1 in THREADS — Lane D is unblocked
Also records what the assembly turned up for the other lanes: the rigSail() door
Lane B's picking adapter must come through, the knockdown(t, ...) argument order
that would have silently broken Lane D's get-up, and the evidence for Lane C's
dispose() light-restoration ask.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 23:38:54 +10:00
m3ultra
6083151af6 Bake M3 animation pack: 11 new Mixamo clips into player_anims.glb
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-16 23:06:40 +10:00
m3ultra
41ad12dede Merge all lanes; add importmap; fix /world/ absolute paths
Selftest on merged main: 121 pass / 0 skip / 0 fail.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-16 22:23:20 +10:00
m3ultra
31d9946a04 Merge remote-tracking branch 'origin/lane/d' 2026-07-16 22:14:20 +10:00
m3ultra
e7639c4264 Merge remote-tracking branch 'origin/lane/c'
# Conflicts:
#	THREADS.md
2026-07-16 22:14:20 +10:00
m3ultra
8791eccc08 Merge remote-tracking branch 'origin/lane/e'
# Conflicts:
#	THREADS.md
2026-07-16 22:14:09 +10:00
m3ultra
703dbc499f Log Lane B landing, unit change and two findings in THREADS
Flags for other lanes: load/rating are newtons now (HUD shows kN); the
yard's 7 anchors only admit 70-192 m2 quads when real shade sails are
20-50 m2; and flat-horizontal is currently the lowest-load geometry,
which inverts DESIGN.md's central shade-vs-survival tension and can't be
fixed inside sail.js.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 21:55:37 +10:00
m3ultra
6382e604b8 Lane D: the small person — player, interactions, selftests
player.sim.js  Deterministic core, zero imports: camera-relative movement, the
               state-machine table, wind slow/gust-shove/knockdown. step(dt,t)
               is the whole clock — no Date.now, no Math.random, no rAF — so a
               storm fast-forwards identically in selftest and in the game.
player.js      The view: rig load per the 90sDJsim DEVMANUAL rig rules
               (SkeletonUtils.clone, height-normalise off the MEASURED head
               bone, canonicalised bone namespace), clip retarget, and
               createPlayer() satisfying the Player contract.
interact.js    Hold-E with radial progress + wireYardActions (re-rig 2.5 s,
               turnbuckle trim 1.2 s, carry-one-item), duck-typed so it no-ops
               cleanly until Lane B lands sailRig.repair/trim.
d.test.js      20 asserts in Lane A's harness: 38 pass / 3 skip overall.

Ported from the 2D prototype's shape (game.js:250-252), retuned to m/s: the
slow curve, and shove gated to gusts only and scaling with speed² so gusts have
teeth. Knockdown needs 0.5 s of SUSTAINED overload — deliberately the same rule
as a sail corner letting go, so cloth and people speak one language.

Two decisions worth the review:
- The knockdown pitches the root in code rather than playing the Falling clip's
  root. Shared clips must drop Hips.quaternion (a different-orientation source
  lays the target flat), so a clip physically cannot lie the body down. Doing it
  in code also lets the fall go DOWNWIND of the gust that caused it, which a
  canned clip could never do, and keeps it deterministic.
- Gust magnitude is recovered from a slow EMA of local wind rather than widening
  Lane C's contract: wind.sample() gives the total and gustTelegraph() only fires
  BEFORE a gust, so nothing reports gust size during the hold. The EMA
  self-calibrates to whatever storm JSON Lane C authors.

Verified in a real scene, not only in asserts: head bone 1.715 m at fig scale
0.983, all six clips bound, walk/run at the tuned speeds, the body lies down and
gets back up, hold-E fires exactly once per press.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 21:55:16 +10:00
m3ultra
31a887bf75 Log Lane C landing, contract note and per-lane asks in THREADS
Also corrects the worktree-collision attribution: the checkout that moved HEAD
off lane/a was mine, not Lane D's.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 21:53:00 +10:00
m3ultra
302972cc6e Fill in Lane E selftest suite: assets verified in three.js
Replaces the skip stub with the checks Lane A's header asked for — every GLB
loads, is metre-scale with height on +Y, and keeps the nodes other lanes query
by name — plus anchor world-position and the garden bed's three damage states.

This catches what the Blender side structurally cannot: Blender exports
Z-up->Y-up and imports Y-up->Z-up, so a broken export_yup round-trips green.
A native glTF reader is the only thing that can prove the file.

GLTFLoader is imported dynamically on purpose. Three.js addons import the bare
specifier `three`, no page in the repo has an importmap yet, and selftest.html
turns an un-importable lane module into a hard FAIL — so a static import would
redden Lane A's merge gate over a harness gap rather than a real defect. It
skips with the fix instead, and lights up by itself once the importmap lands.
Verified behind a temporary probe first: 36/36 pass. Need logged in THREADS.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 21:50:43 +10:00
m3ultra
219dd55716 Log Lane E landing and PLAN3D asset-path corrections
PLAN3D §2's inventory was verified against the M1 Ultra, but we build on the
M3 Ultra, where several of those libraries are absent or moved. Records the
real paths and flags the gaps that block Lanes A and D, plus the node/anchor
contracts other lanes consume.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 21:42:40 +10:00
m3ultra
8d76340f49 Log the shared-worktree collision in THREADS
Lane D is working in the shared ~/Documents/shades checkout rather than its own
clone, so its git checkout moved HEAD off lane/a mid-session and Lane A's M0
commits landed straight on main. No damage this time, but two agents sharing one
HEAD and one index will eventually eat someone's uncommitted work.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 21:36:44 +10:00
m3ultra
868ea5699d Correct PLAN3D asset inventory; log M0 contract additions
§2's paths were substantially wrong. Re-verified against the filesystem:
3D-STORE is at ~/Documents/Destroyulater/3D-STORE (its clean_glbs debris set is
real, just relocated), while 3D=models/, character_kit/, mixamo-fetch/ and FBX/
do not exist on this box at all. That last group is Lane D's whole animation
pipeline, so it's flagged loudly rather than quietly patched.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-16 21:33:42 +10:00
m3ultra
8338c0fa99 Add 3D execution plan, lane prompts, and THREADS log
PLAN3D.md: locked stack (vendored three.js r175 + stdlib server, DJsim
house style), verified asset inventory on the M1 Ultra, module contracts,
five parallel lanes (world/sail/weather/player/assets) with acceptance
criteria and integration order.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-16 21:05:57 +10:00