Everything lives in .spb-scene: position: relative, width: 100%, aspect-ratio: 16 / 10 capped by max-height: 340px (its height comes from these two rules alone, since every child is absolutely positioned), overflow: hidden, isolation: isolate, rgb(12, 16, 34) background, 14 px corners, and the font stack Inter, -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif declared once and inherited by the headings, the paragraphs and the pill. Inside, three absolutely positioned children. .spb-scroll (inset: 0, overflow-y: auto, padding: 22px 22px 22px 40px, scroll-behavior: smooth) holds the text — six 16 px h4 and six 13 px / 1.7 p — and hides its native scrollbar with scrollbar-width: none backed by ::-webkit-scrollbar { width: 0 } (measured: offsetWidth = clientWidth, no gutter). .spb-beam, the rail: left: 14px, top: 18px, bottom: 18px, 4 px wide, white at 10%, z-index: 3, pointer-events: none — so it measures the box height minus 36 px (304 px under the cap). Its fill .spb-beam-fill has a height of calc(var(--spb-p, 0) * 100%), an rgb(92, 255, 216) → rgb(109, 139, 255) gradient and two shadows (12 px blue at .8, 4 px mint at .9); the dot .spb-beam-dot, 12 px white, 0 0 14px 3px halo, sits at top: calc(var(--spb-p, 0) * 100%) and is re-centred by translate(-50%, -50%). .spb-pct, the pill (right: 14px, top: 12px, 12 px, tabular-nums, black at 40%), shows the percentage.
The JavaScript is an ES5 IIFE that handles every .spb-scene on the page (measured with two instances: 0% and 25%, independent). Its update() computes max = scrollHeight − clientHeight, then p = scrollTop / max (0 when max ≤ 0), writes --spb-p on the rail with toFixed(4) and the text Math.round(p × 100) + '%' into the pill — if there is one. It runs once at initialisation, on every scroll of the box ({ passive: true }) and on every window resize. No transition, no easing: the rail follows the scroll frame by frame. Measured in Chromium on a blank 1,280 px page, 1,264 × 340 px box, 125 px of travel: one 60 px wheel notch gives 0.4800 → "48%", 145.9 px of fill on a 304 px rail and the dot's centre at exactly 145.9 px; 0.9600 on the second notch, 1.0000 on the third, "100%", the dot overhanging the rail by 6 px (the translate); wheel back, 0.0000 again. 200 calls to update() cost 0.2 ms. scroll-behavior: smooth only affects programmatic scrolls: scrollTo(max) fires 21 scroll events and reaches 1 in ≈ 170 ms — a single event under prefers-reduced-motion, where the rule switches to auto.
The height is the part of the code to understand before touching it. Every child of .spb-scene is absolutely positioned: without aspect-ratio the box would be 0 px tall, and with the ratio alone it would grow with its width — on a 1,280 px page, 790 px tall for 465 px of sold content (text, margins and padding), so scrollHeight = clientHeight, max = 0 and a rail frozen at 0%; that is what max-height: 340px prevents. Measured on a blank page with the sold text: at 1,280 px as at 960, the box is 340 px tall, for 125 px of travel (1,280) or 257 px (960); the cap stops acting below 544 px wide, where the ratio takes over — 290 px tall and 462 px of travel in a 480 px column, 234 px and 606 px on a 390 px phone. The rule to remember: the travel is scrollHeight − clientHeight, i.e. the text, its margins and the 44 px of padding minus the box height, and update() returns 0 as soon as it is no longer positive; with your own text, longer than six paragraphs, replace the cap with the height of your layout. Three more choices in the code: the font-family is declared once on .spb-scene (measured: Inter on the headings, the paragraphs and the pill, with no inline style at all); the dot's halo travels with it but both box-shadow values are constant, identical at 0% and at 100% — the position moves, not the intensity; and @media (prefers-reduced-motion: reduce) switches scroll-behavior to auto, which is what the demo copy announces. The resize listener on window, for its part, is never removed: if you destroy a scene dynamically, remove it too.
ES5 code (var, function), one CSS variable read by two calc(), one { passive: true } listener. The real floor is aspect-ratio: without it, .spb-scene has no height at all, since every child is absolutely positioned; max-height only caps that height. scroll-behavior (Safari 15.4) and scrollbar-width (Chrome 121, Safari 18.2, covered before by ::-webkit-scrollbar) are cosmetic. The rail is driven by JavaScript, not by animation-timeline: it works in Firefox, which no version of scrolls natively in CSS — that is what sets it apart from Scroll Progress Bar (fx-0547) and Progress Bar (fx-0555). Zero dependencies: no library, no image, no font to load — the Inter, -apple-system, … stack falls back to the system font when Inter is not installed.