ludic.lab: lab_png_write / lab_png_write_from (raw 8-bit, 1-4 channels, stored deflate) in png_write.ludic,
importable alone with its own LabPngState; png_convert.ludic's previews of float textures (R32F min..max,
RG16F x255, HDR x/(1+x) + sRGB); lab_ppm_to_png on the same encoder.
render3d: bake_load.ludic - impostor_from_baked / impostor_source / impostor_refill (a fog re-open reads
the bake), sky_baked_in and sky_precompute trying the bake at the start yaw (sky_compute is the
convolution, and sky_ibl_bytes always uses it), carpet_from_baked / carpet_bytes / carpet_finish,
bake_part_count / _len / _off. Compile-only: nothing run.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Both constants were worked out by hand and a byte off each: the tiles' bake wrote "LAAK" and "LDT2", which
ludic bake --check refuses, and r3d_baked_read, holding the same wrong constant, would have refused
ludic.base's correct files (the sun's shadow among them) while accepting its own. Now 0x4B41424C and
0x3254544C, checked against the strings; the unused LTT1 constant is gone. A re-bake is needed.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Each pair runs the work as the renderer always has and reads the result back, or makes the same
textures and fills them from bytes instead: impostor_bytes / impostor_from_bytes (and impostor_fill,
for a fog that opens past a layer's cards), terrain_shadow_bytes / terrain_shadow_from_bytes,
sky_ibl_bytes / sky_ibl_from_bytes (sky_precompute split into sky_ibl_make and the convolutions).
A bundle is a word count, a word length per part and the parts (bake_pack / bake_unpack), checked
against the textures' shapes before any byte is used. gpu_vk_readback.ludic reads a texture's level 0,
every layer, as stored; r3d_baked_read reads a bake's file (ludic.base's LBAK header: key and version
must match) since render3d cannot import ludic.base. Nothing calls them yet: behaviour unchanged.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>