/* Full-viewport fixed backdrop. Sits behind the detail content (.mix-detail-foreground is z-index:1) and never intercepts pointer events — except the zoom slider, which re-enables them on itself. */ .mix-waveform-bg { position: fixed; inset: 0; z-index: 0; pointer-events: none; overflow: hidden; } /* The canvas fills the viewport. All ribbon shading (luminous depth, soft edges) is drawn inside the canvas by the WebGL2 fragment shader. NO CSS backdrop-filter: it was a confirmed per-frame perf killer on the Canvas predecessor and is exactly the cost the GPU move exists to eliminate (spec §2, §5.2); the glass treatment returns in-shader in Wave 3. */ .mix-waveform-canvas { position: absolute; inset: 0; width: 100%; height: 100%; display: block; } /* Zoom slider — a small viewing control pinned to the top-right, clear of the player bar at the bottom and the nav bar at the top. It is never a seek surface. top: 5rem sits just below the fixed nav bar (~4.5rem tall) so neither the expanded player bar nor the nav occludes it. position: fixed (not absolute) because the slider is now a top-level sibling of the backdrop, not a child of it — see the comment in the .razor. z-index: 10 lifts it above the page foreground (.mix-detail-foreground, z-index: 1) so the foreground can't intercept its pointer events; that occlusion was the resolution-slider regression. */ .mix-waveform-zoom { position: fixed; right: 1.5rem; top: 5rem; z-index: 10; width: 180px; max-width: 40vw; pointer-events: auto; opacity: 0.7; transition: opacity 0.2s ease; } .mix-waveform-zoom:hover { opacity: 1; }