LoadingMark
SourceThe clear mark as a loading status. Three bar strips inside the circle, each sweeping from its thin end, the middle one reversed.
Native
The mark is measured from the logo: three bands on a constant pitch, the outer two thin to thick, the middle thick to thin and reaching the wider chord. Every bar grows from its thin end the way the homepage strips reveal, 0.02s apart over 0.3s, holds, then empties the same way.
<LoadingMark />
Sizes
The composition always animates at 180 by 182 px, where the thinnest bar is still two pixels. A smaller size scales that layer down as a whole instead of laying bars out under a pixel.
<LoadingMark size={90} />
<LoadingMark size={45} />
<LoadingMark size={24} />Tone
Foreground ink by default. Inverse ink for a foreground ground. current inherits the parent's color.
<Box backgroundColor="foreground" padding="6">
<LoadingMark tone="inverse" size={90} />
</Box>Chase
Each band starts a third of a period after the one above it, so the bands rest at different times and the mark never goes blank. A chase of 0 runs them in step: the mark fills and empties as one, and rests empty for a third of a second each cycle.
<LoadingMark chase={0} />Inline
Small, beside a line of copy, for a wait inside a flow. Name what is loading and assistive tech reads the name, not three strips.
Confirm in your wallet
<Box alignItems="center" columnGap="3">
<LoadingMark size={20} label="Signing" />
<Text variant="small" color="muted">Confirm in your wallet</Text>
</Box>Cost
The 53 bars are 53 compositor layers, each animating transform and nothing else: no layout, no paint, and the sweep keeps drawing while the main thread is blocked. On a page with an IntersectionObserver (next's Link prefetch) or an animationiteration listener (react's root), chrome still samples every running animation on the main thread each frame, so the budget is per running animation: one mark is 53. Keep the marks visible at once to a few. A gate in the e2e lane pins every count, with controls it proves red.
The lab renders n marks under a variant, and the record with the numbers is docs/lens/loading-mark-perf.md.
Props
LoadingMark is a div. Every div attribute passes through.
The rendered width in px. The mark animates at its native 180 and scales to this.
Foreground ink, inverse ink for a foreground ground, or the parent's color.
Seconds for one sweep cycle: fill, hold, empty, rest.
Seconds each band starts after the one above it. A third of the period by default, so one band is always showing. 0 runs them in step.
The accessible name. The mark is the status, the bands are decoration.