Commit Graph

2 Commits

Author SHA1 Message Date
m3ultra
9ef0941ac4 factory: palette hexes reach the screen — sRGB->linear in hex_to_rgba, pinned
hex_to_rgba put sRGB fractions straight into Blender's LINEAR Base Color
socket, so baseColorFactor shipped linear-encoded-as-sRGB and three's
linear->sRGB display step made every surface one gamma step too light
and desaturated, on every asset, since Sprint 1. Measured: leaf_gum
#7C8F5E displayed #B9C5A3, bark_gum #BFB8A8 displayed #E0DDD4 (the
near-white gum trunk THREADS blamed on Blender's view transform).

Fixed at source with the exact IEC curve (alpha untouched — coverage,
not colour) and the whole factory rebuilt: ALL ASSETS PASS. e.test now
pins mat.color.getHexString(SRGBColorSpace) against the authored PAL hex
— factory intent vs what the runtime draws, the one comparison neither
end can fake. Mutation-checked red-then-green against the pre-fix GLB.
523/0/0, verified by eye in the running game before and after.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-28 21:26:26 +10:00
m3ultra
f2527055a5 Add hail juice, plant shred, and a way to screenshot the game
Hail (SPRINT5 §E-1) ships two ways because Lane C's rain is a BoxGeometry with a
flat material and skyfx loads no external texture at all: hail_stone_01 as
geometry that drops into their existing InstancedMesh pattern, and hail_pips.png
as a 4-cell atlas for impacts. A flat quad can't be round and an impact is round
— that's the only reason the atlas is a texture. Both come with a copy-paste
recipe, because a grep showed exactly one of my five shipped textures is
consumed: sail_weave, the one I wrote a recipe for. grass_atlas has sat
unreferenced for four sprints.

plant_shred (§E-2) is elongated after the first pass came out radial and read as
green potatoes — it's the long axis plus the midrib that says "leaf".

tools/yardshot/ finally lands the DESIGN.md pictures, carried since Sprint 2. It
does NOT touch server.py or main.js: it's a Lane E stdlib server that serves the
repo and takes POST /shot, so the browser posts a Blob and bytes go straight to
disk instead of base64 through a console. do_POST is ~25 lines and Lane A is
welcome to lift it and delete this.

Three traps found on the way, all documented: toBlob is async so the WebGL buffer
is already cleared (toDataURL is sync); a backgrounded tab lays the canvas out at
0x0 and toDataURL then returns "data:,"; rAF is paused there so step() must be
driven by hand.

Selftest 209/0/0, 36 output files byte-identical across two runs.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-17 03:03:54 +10:00