#323
Reading progress bar
A 4px bar stuck to the top of an article fills from left to right as it is read, with a percentage readout, tied directly to scroll position.
Hand this to your AI. It names the exact library parts, timings and accessibility promises of this demo.
Build the "Reading progress bar" pattern (@codeatlasdev/ui demo #323, motion/scroll) in my app.
Call get_demo({ ids: ["#323"] }) first and keep its structure. It needs @codeatlasdev/[email protected].
Use: Long articles, docs and legal pages where the reader wants to know how far they are.
Keep these library parts, with the props and tokens the demo uses:
- MotionStage, MotionCtx from "@codeatlasdev/ui"
Behaviour to keep:
- `MotionStage` from `@codeatlasdev/ui` with `loop={5200}`: autoplay scrolls the article, a wheel or touch scroll takes over
- `.doc__bar` is `position: sticky;` with `block-size: 4px;` and holds a fill scaled with `transform: scaleX(var(--p));` from `transform-origin: left center;`
- Native: `animation-timeline: scroll(nearest block)` with `@keyframes fill` from `scaleX(0)` to `scaleX(1)`, inside `@supports (animation-timeline: scroll())`
- Fallback and readout: a `scroll` listener computes `el.scrollTop / max` (`max` is `el.scrollHeight - el.clientHeight`); the percentage is `Math.round(p * 100)`
- Autoplay reads the article in `3600` ms, linear like a steady reader
- Under reduced motion the bar is full and the readout shows 100%
Exact motion (do not approximate):
- transform: scaleX: animation-timeline: scroll(nearest block), linear
Reduced motion: the demo handles it; keep that branch.
Keyboard: operable; keep the focus order and key handling.
Change only the copy and the data. Use the theme tokens (--ca-*), never raw colours. Library parts
- MotionStage
@codeatlasdev/ui
How it is built
- `MotionStage` from `@codeatlasdev/ui` with `loop={5200}`: autoplay scrolls the article, a wheel or touch scroll takes over
- `.doc__bar` is `position: sticky;` with `block-size: 4px;` and holds a fill scaled with `transform: scaleX(var(--p));` from `transform-origin: left center;`
- Native: `animation-timeline: scroll(nearest block)` with `@keyframes fill` from `scaleX(0)` to `scaleX(1)`, inside `@supports (animation-timeline: scroll())`
- Fallback and readout: a `scroll` listener computes `el.scrollTop / max` (`max` is `el.scrollHeight - el.clientHeight`); the percentage is `Math.round(p * 100)`
- Autoplay reads the article in `3600` ms, linear like a steady reader
- Under reduced motion the bar is full and the readout shows 100%
Related
Loading source.