Refined lighting. Protected movement.
One focused pass for owner review. Open the interactive test →
Checkpoint and protected behaviour
The complete browser directory was copied before editing and saved as a ZIP. Git history was bundled, and commit 98cbcf4 tagged browser-owner-tested-20261016. The prior immutable Pages deployment is retained. All canonical GLBs, geometry metadata and mesh buffers have matching before/after hashes. The motion quaternion code, gains 0.5 / 0.45, limits 45° / 20°, 120 ms smoothing, camera loop, touch, pinch, recenter and full-screen handlers are byte-identical. Palette colour constants, material identities, acrylic thickness and mounting datums are unchanged.
Exact changes
| Area | Change | Purpose and cost |
|---|---|---|
| Mirror illumination | Derived the existing 2K and 1K HDRs with excess blue B − max(R,G) reduced by 85%; 10% of that excess added to red and 5% to green, then linear luminance restored before RGBE encoding. | Reduces blue contamination while preserving foliage, spatial detail and HDR range. No painted reflection pattern, new reflection pass, or per-frame colour-processing loop. |
| Exposure and contrast | Environment intensity 0.8 → 0.6; key intensity 2.1 → 1.8 with neutral white instead of warm white; point fill 0.30 → 0.22; hemisphere intensity 0.35 → 0.18 with neutral sky colour instead of blue. | Deeper acrylic and less pale reflected areas. Light positions, environment orientation, tone map and exposure 1.3 retained. The existing sharp mirror sampling and Fresnel response remain angle-dependent. Gold and silver retain their original RGB, metallic and roughness values. |
| Wall | Linear RGB 0.42 / 0.30 / 0.16 → 0.62 / 0.52 / 0.35; roughness 0.88 → 0.94; bump amplitude 0.14 → 0.08 mm. | Matte cream appearance under the reduced lighting, with subtler plaster texture. Wall appearance is a renderer-side adjustment; manufacturing colours are untouched. |
| Wall occlusion | 32 cosine-weighted hemisphere samples projected from every canonical mesh triangle onto the actual wall plane; 768 × 640 maps, 1.2-texel denoise, applied to wall indirect diffuse at 65% strength. | Separate standoff and adhesive maps respect their different clearances. 9,791 / 6,944 bytes. One texture read in the existing wall shader; no added draw call, SSAO pass, ray tracing or screen-space effect. |
| Directional shadows | Existing 1024² VSM, radius 8 and 8 blur samples retained. Shadow maps update at initialization and when quality changes, rather than on every camera frame. | The world is static; camera movement does not change these shadows. Measured draw submissions fell from 20 to 9 per frame. Shadow behaviour must be invalidated if future work moves geometry or lights. |
| Colour switching and loading | Removed unnecessary material recompilation request on colour changes. Wall occlusion loads in parallel with geometry. Entry points revalidate and the application script is versioned. | Uniform-only colour updates remain immediate. The same public URL serves the new build without replacing heavy cached vendor files. |
Visual checks





Silver is less blue, the face is deeper, and contact grounding is visible without changing spacing. Gold remains warm in the oblique view. The retained HDR source, recorded camera and viewport allow a useful reference check, but this is not a formal identical-lighting validation: renderer light transport, calibrated intensities, wall material, tone mapping and local reflections differ. No live Unreal session was opened or altered. The formal blind comparison remains separate.
Performance comparison
Windows Chrome 152, NVIDIA Quadro K2200, 390 × 844 touch viewport, DPR 2, identical synthetic 60 Hz orientation trajectory. Each initial run sampled 20 seconds of movement. These are desktop measurements, not Android sensor-to-photon, battery or thermal measurements.
| Quality | FPS before → after | p95 frame | Worst frame | Mean event → render | Resource bytes |
|---|---|---|---|---|---|
| high | 60.00 → 60.00 | 16.8 → 16.8 ms | 17.1 → 25.6 ms | 8.69 → 8.57 ms | 8.323 → 8.275 MB |
| low | 60.00 → 60.00 | 16.8 → 16.8 ms | 16.9 → 17.1 ms | 8.38 → 8.57 ms | 3.376 → 3.372 MB |
There was one 25.6 ms frame in the first refined high-quality run; p95 and average frame rate did not regress. This is reported rather than discarded. No sustained regression was observed in the tested scope; physical-phone confirmation remains necessary.
30-second high-quality confirmation (baseline-confirm): 60.00 FPS average; 16.8 ms p95; 17.0 ms worst frame; 8.59 ms mean synthetic event-to-render.
30-second high-quality confirmation (refined-confirm): 60.00 FPS average; 16.8 ms p95; 16.9 ms worst frame; 8.48 ms mean synthetic event-to-render.
Initial one-off first-frame measurements: high 2,019 → 2,191 ms; low 1,003 → 1,136 ms. After loading the new wall map in parallel with geometry, three alternating fresh browser-context high-quality loads had medians 968 → 933 ms. Browser contexts are fresh, but OS/driver shader caches are not reset; these numbers do not establish cellular or physical-device load time.
High-quality resource payload fell by about 48 KB and battery saver by about 4 KB in the initial runs. There is one additional 768 × 640 wall texture, approximately 2.6 MB including an RGBA mip chain on implementations using RGBA storage. No new per-frame render pass is introduced. Battery saver still uses DPR 1, a 1K HDR and no directional shadow pass; it retains the inexpensive baked wall occlusion.
Verification and acceptance
Both mounting variants, two visible standoff caps, exact geometry hashes, synthetic motion, drag, pinch, recenter, instant colours, full-screen, landscape and low/high quality transitions passed. No page errors were observed. Checks · Protected-code and geometry hashes · Derived asset provenance · Repeated loads.
Reload the existing Android URL, compare Silver and Gold while tilting, inspect Anthracite and the wall contact, and confirm movement feels as immediate as checkpoint 01. If the phone struggles, select Battery saver. The work stops here for owner review. No catalogue expansion, Manager change, Unreal V1 change, streaming dependency or GPU-capacity work is included.