Picks a number, or a range with two thumbs, by dragging along a track. Shows the formatted value.
import { Slider } from "@rdloom/react";
export default function SliderBasicExample() {
return (
<div className="w-72">
<Slider label="Volume" defaultValue={40} />
</div>
);
}Installation
npx rdloom add sliderCopies the source into src/components/rdloom. Edit it freely: rdloom upgrade merges later versions into your changes. It needs react-aria-components; add --install to install them.
Use another registry client
npx shadcn@latest add https://rdloom.vimalbhatt.com/r/slider.jsonWorks, but without upgrade tracking.
Usage
import { Slider } from "@rdloom/react";
<div className="w-72">
<Slider label="Volume" defaultValue={40} />
</div>Range
Searching ages 20–60
import { useState } from "react";
import { Slider } from "@rdloom/react";
export default function SliderRangeExample() {
const [committed, setCommitted] = useState<number | number[]>([20, 60]);
return (
<div className="flex w-72 flex-col gap-2">
{/* Two values make two thumbs. onChangeEnd fires once, when the user lets go. */}
<Slider label="Age" defaultValue={[20, 60]} minValue={18} maxValue={99} onChangeEnd={setCommitted} />
<p className="text-sm">Searching ages {Array.isArray(committed) ? committed.join("–") : committed}</p>
</div>
);
}Currency
import { Slider } from "@rdloom/react";
export default function SliderCurrencyExample() {
return (
<div className="w-72">
{/* formatOptions is what's shown and what screen readers announce: "$250". */}
<Slider
label="Budget"
defaultValue={250}
maxValue={1000}
step={50}
formatOptions={{ style: "currency", currency: "USD", maximumFractionDigits: 0 }}
/>
</div>
);
}Disabled
import { Slider } from "@rdloom/react";
export default function SliderDisabledExample() {
return (
<div className="w-72">
<Slider label="Brightness" defaultValue={70} isDisabled />
</div>
);
}API Reference
Defined by the spec. Components also accept the props of the React Aria component they wrap.
| Prop | Type | Default |
|---|---|---|
labelrequiredVisible label, also the accessible name. | string | none |
minValueLowest value. | number | 0 |
maxValueHighest value. | number | 100 |
stepAmount each arrow key press changes the value by. | number | 1 |
valueControlled value. An array of two numbers makes a range slider. | number | number[] | none |
defaultValueInitial value when uncontrolled. An array of two numbers makes a range slider. | number | number[] | none |
formatOptionsHow the value is shown and announced, e.g. { style: 'currency', currency: 'USD' }. | Intl.NumberFormatOptions | none |
showValueShows the formatted value next to the label. | boolean | true |
isDisabledPrevents interaction and dims the slider. | boolean | false |
onChangeCalled continuously while the value changes. | (value: number | number[]) => void | none |
onChangeEndCalled once when the user finishes, e.g. to run a search. | (value: number | number[]) => void | none |
Accessibility
Role slider, WCAG 2.2 AA. Tested with axe and keyboard tests; screen reader checks are in the audit checklist.
Keyboard
- Tab moves to each thumb
- Left/Down Arrow decreases by one step; Right/Up Arrow increases
- Page Up/Page Down change by a larger step
- Home and End jump to the minimum and maximum
Screen readers announce
- Each thumb is announced as a slider with the label and formatted value
- Arrow keys announce each new value
- In a range, thumbs are announced as the minimum and maximum of the label
What your code must do
- Each thumb is a native range input, labelled by the slider's label (range thumbs say minimum or maximum)
- The value text uses formatOptions, so screen readers hear $250, not 250
- Range thumbs can't cross each other
- The thumb is at least 24px, for touch
Guidelines
Use it when
- An approximate value in a known range, like price or volume
- Filters where the exact number matters less than the feel
Avoid it when
- Exact values: use a number TextField
- Very large ranges where a step is meaningless
Don't
- Hiding the value: show it, so users know where they are
- A slider as the only way to enter a precise number
Design tokens
The semantic tokens this component uses. Change them once and every component follows; see Design tokens.
--rd-color-action-primary--rd-color-surface-subtle--rd-color-surface-raised--rd-color-border-strong--rd-color-text-default--rd-color-text-muted--rd-color-focus-ring