Donut Chart
Donut and pie charts bent from neon tube, with a lit hover, keyboard reading and an unlit remainder for max.
| Segment | Value | Share |
|---|---|---|
| Direct | 18,240 | 43% |
| Organic search | 12,906 | 30% |
| Referral | 6,118 | 14% |
| Social | 3,402 | 8% |
| 1,977 | 4.6% |
Installation
npx shadcn@latest add https://neonkit.heyaadi.com/r/donut-chart.jsonUsage
import { DonutChart } from "@/components/ui/donut-chart"
<DonutChart
label="Sessions this week"
data={[
{ label: "Direct", value: 18240 },
{ label: "Organic search", value: 12906 },
]}
/>Examples
Part of a whole
max sets the whole. What the segments don't use stays as an unlit run of tube. Segments too short to bend become beads.
Pie
Wedges of tinted glass, each edged with a tube along its outer arc and pulled apart by gap.
Compact
One segment and a max make a small gauge. centerLabel={null} leaves just the number.
API reference
className and style go on the outer element, which holds the chart and the legend.
| Prop | Type | Default |
|---|---|---|
data | { label: string; value: number; color?: NeonColor }[]Segments clockwise from the top. The first defaults to --neon, the rest to a fixed palette. | None |
variant | "donut"Tubes, or glass wedges edged with tube. | "donut" |
size | numberDiameter in pixels. | 220 |
thickness | numberTube thickness as a share of the diameter, 0.03 to 0.2. | 0.075 |
gap | numberPixels between segments, on top of the round ends. | 3 |
max | numberThe whole. Any remainder shows as unlit tube and gets its own legend and table row. | None |
label | stringWhat the chart measures. Captions the total and the data table and leads the summary. | None |
centerLabel | ReactNodeCaption under the centre value. null hides it. | label |
remainderLabel | stringName of the remainder when max leaves one. | "Remaining" |
formatValue | (value: number) => stringFormats values in the centre, legend, table and announcements. | None |
activeIndex | numberControlled lit segment. null lights them all. | None |
defaultActiveIndex | numberInitial lit segment when uncontrolled. | null |
onActiveIndexChange | (index: number | null) => voidCalled on hover, focus and arrow keys. | None |
showLegend | booleanLegend with value and share. It wraps under the chart when there's no room beside it. | true |
hideCenter | booleanHides the centre readout. Pies never show one. | false |
animate | booleanDraws the tubes on round the ring when the chart scrolls into view. | true |
color | NeonColorColor of the first segment. | inherited |
Accessibility
- The chart is an image named by a summary of every segment, with a visually hidden table of the same data.
- Tab focuses it; arrow keys move between segments, Home and End jump to the ends and Escape clears. Each move is announced.
- With reduced motion the tubes appear fully drawn and hover changes are instant.