ProgressRing
Every example on this page is live, drawn by the library's Storybook, where you can also change its props and see the result.
A ring that fills clockwise from twelve o'clock to show a percentage, with the percentage in its middle. Adapts to dark mode.
Size it in CSS (size="100%", or size="fill" for the room its flex parent leaves) rather than in
pixels worked out from your layout: the ring stays round, its stroke and text scale with it, and it
shrinks with its box in a saved render. A label names what it measures under the percentage, so
the ring and its name are one block.
Import
import { ProgressRing } from "~lib/data-display/progress-ring";
Props
| Name | Type | Required | Default | Description |
|---|---|---|---|---|
percentage | number | Yes | N/A | Progress (0-100), clamped |
size | number | string | "fill" | No | 100 | Width in pixels, any CSS width such as "100%", or "fill"; always round |
strokeWidth | number | No | 8 | Ring thickness in px, or in hundredths of the ring's width with a CSS size |
showLabel | boolean | No | true | Show the percentage |
label | string | No | N/A | What the ring measures, such as "of the year", set smaller under the percentage |
Examples
50%
100%
Custom Size
No Percentage
With a Label
Set label to name what the ring measures. It sits under the percentage, smaller, and the two are
centered on the ring together. It is set at a share of the ring, and smaller still when a long
label would run into the ring, so keep it to a word or two. With showLabel={false} the label sits
alone in the middle.
Sized to Its Box
A pixel size stays that many pixels, so a ring whose size you worked out from the layout keeps
them in a saved render laid out again in a smaller box. Give it a CSS width instead: the ring is
drawn at its default size and scaled to its box, stroke and text together, so it keeps its
proportions at any size and strokeWidth is in hundredths of its width:
size="fill" lets the ring take the room its flex parent leaves. Down a column it grows to the
column's width and is the first thing to give way when the column runs short, so the text around it
always fits; across a row it takes the row's height, which the row needs of its own. The ring is
the shorter side of that room either way, centered:
<div className="flex min-h-0 flex-1 flex-col gap-2">
<Heading level={4}>Spring term</Heading>
<ProgressRing percentage={share} size="fill" label="of the term" />
</div>
See Also
- DonutGauge - Donut chart for ratios
- BarIndicator - Linear progress bar
- Stat - Metric display