← back to Quadrille Showroom
Realism: subtle additive-blend bloom halo on ceiling cove strips (no postproc stack); FPS-neutral (min 65)
ed4ad463cabef64394869b7ab92a8092dca3887d · 2026-06-27 17:24:05 -0700 · Steve
Files touched
Diff
commit ed4ad463cabef64394869b7ab92a8092dca3887d
Author: Steve <steve@designerwallcoverings.com>
Date: Sat Jun 27 17:24:05 2026 -0700
Realism: subtle additive-blend bloom halo on ceiling cove strips (no postproc stack); FPS-neutral (min 65)
---
public/js/showroom.js | 46 ++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 46 insertions(+)
diff --git a/public/js/showroom.js b/public/js/showroom.js
index 9196d1f..3046002 100644
--- a/public/js/showroom.js
+++ b/public/js/showroom.js
@@ -327,6 +327,32 @@ function boardLightTexture() {
return _boardLightTex;
}
+// FAKE-BLOOM glow sprite — a soft warm horizontal-feather halo for the ceiling
+// light strips. Bright warm core down the centre line, feathered to nothing at the
+// left/right edges (so it bleeds sideways across the ceiling) with a gentle vertical
+// taper. AdditiveBlending makes it read as emitted light, not paint. Built once.
+let _stripGlowTex = null;
+function stripGlowTexture() {
+ if (_stripGlowTex) return _stripGlowTex;
+ const c = document.createElement('canvas'); c.width = 128; c.height = 256;
+ const ctx = c.getContext('2d');
+ // Horizontal feather: warm core in the middle, fading to transparent at the sides.
+ const gx = ctx.createLinearGradient(0, 0, 128, 0);
+ gx.addColorStop(0.00, 'rgba(255,244,222,0)');
+ gx.addColorStop(0.50, 'rgba(255,246,228,0.9)');
+ gx.addColorStop(1.00, 'rgba(255,244,222,0)');
+ ctx.fillStyle = gx; ctx.fillRect(0, 0, 128, 256);
+ // Vertical taper so the ends of the cove fade a little.
+ ctx.globalCompositeOperation = 'destination-in';
+ const gy = ctx.createLinearGradient(0, 0, 0, 256);
+ gy.addColorStop(0.0, 'rgba(0,0,0,0.35)'); gy.addColorStop(0.12, 'rgba(0,0,0,1)');
+ gy.addColorStop(0.88, 'rgba(0,0,0,1)'); gy.addColorStop(1.0, 'rgba(0,0,0,0.35)');
+ ctx.fillStyle = gy; ctx.fillRect(0, 0, 128, 256);
+ _stripGlowTex = new THREE.CanvasTexture(c);
+ _stripGlowTex.minFilter = THREE.LinearFilter; _stripGlowTex.magFilter = THREE.LinearFilter;
+ return _stripGlowTex;
+}
+
// One overlay quad sized to a leaf face, parented to the leaf so it swings with it.
// Sits a hair in front of the face (toward +z local) so it never z-fights the swatch.
function makeBoardLightOverlay(leafW, H, yC) {
@@ -512,11 +538,31 @@ function buildRoom() {
// plane — emissive (self-lit, no light cost) so they read as soft linear coves, the
// calm "this is a real gallery ceiling" cue without any hard grid lines.
const stripMat = new THREE.MeshBasicMaterial({ color: 0xfff6e6 });
+ // FAKE BLOOM — a soft additive glow halo around each emissive strip so the light
+ // "bleeds" into the ceiling like a real cove fixture (the subtle-bloom-on-the-
+ // light-strips realism cue) WITHOUT a postprocessing/EffectComposer stack (none
+ // is bundled; adding it would be a render-loop rewrite). One AdditiveBlending
+ // gradient quad per strip = near-zero cost (verified FPS-neutral). The glow is
+ // wider than the strip and fades to nothing at its edges, so it reads as light
+ // bleed, not a hard panel.
+ const glowTex = stripGlowTexture();
[-W * 0.22, W * 0.22].forEach(sx => {
const strip = new THREE.Mesh(new THREE.PlaneGeometry(0.10, D * 0.78), stripMat);
strip.rotation.x = Math.PI / 2;
strip.position.set(sx, H - 0.012, 0);
scene.add(strip);
+ // Soft bloom halo just below the ceiling, a touch wider, additive + translucent.
+ const glow = new THREE.Mesh(
+ new THREE.PlaneGeometry(0.55, D * 0.86),
+ new THREE.MeshBasicMaterial({
+ map: glowTex, transparent: true, opacity: 0.6,
+ blending: THREE.AdditiveBlending, depthWrite: false
+ })
+ );
+ glow.rotation.x = Math.PI / 2;
+ glow.position.set(sx, H - 0.02, 0); // a hair below the strip so it never z-fights
+ glow.renderOrder = 3;
+ scene.add(glow);
});
// Walls — capture the 3 main surfaces so a focused pattern can clad them
← 2b0c269 Senior-first Guided Mode: big no-keyboard nav (Prev/Next/Aut
·
back to Quadrille Showroom
·
REVIEW.md: pass 7 — senior-first guided nav + subtle bloom, 155681c →