Skip to Content

Slider

A draggable range input built on Base UI’s Slider primitive. Supports single values, ranges, horizontal and vertical orientations, and keyboard navigation.

Import

import { Slider } from "chunks-ui";

Basic Usage

<Slider.Root defaultValue={40}> <Slider.Control> <Slider.Track> <Slider.Indicator /> <Slider.Thumb aria-label="Value" /> </Slider.Track> </Slider.Control> </Slider.Root>

With Value Display

Use Slider.Value to display the current value. Place it anywhere inside Slider.Root:

<Slider.Root defaultValue={60}> <div className="flex items-center justify-between"> <span className="text-sm text-muted-foreground">Volume</span> <Slider.Value /> </div> <Slider.Control> <Slider.Track> <Slider.Indicator /> <Slider.Thumb aria-label="Volume" /> </Slider.Track> </Slider.Control> </Slider.Root>
Volume60

Range Slider

Pass an array to defaultValue and render a Slider.Thumb with index for each handle:

<Slider.Root defaultValue={[20, 80]}> <Slider.Control> <Slider.Track> <Slider.Indicator /> <Slider.Thumb index={0} aria-label="Minimum" /> <Slider.Thumb index={1} aria-label="Maximum" /> </Slider.Track> </Slider.Control> </Slider.Root>
Price range20 – 80

Vertical Orientation

Set orientation="vertical" on the root. The track and indicator switch to a vertical layout. A vertical slider fills its parent’s height (h-full), so give the parent a height, or it collapses:

<div className="flex h-40"> <Slider.Root defaultValue={50} orientation="vertical"> <Slider.Control> <Slider.Track> <Slider.Indicator /> <Slider.Thumb aria-label="Value" /> </Slider.Track> </Slider.Control> </Slider.Root> </div>

Controlled

Slider.Root infers whether its value is a number or an array from value or defaultValue, so a typed useState setter is an onValueChange. A range (useState([20, 80])) works the same way:

function ControlledSlider() { const [value, setValue] = useState(50); return ( <Slider.Root value={value} onValueChange={setValue}> <Slider.Control> <Slider.Track> <Slider.Indicator /> <Slider.Thumb aria-label="Value" /> </Slider.Track> </Slider.Control> </Slider.Root> ); }

Disabled

A disabled Slider is dimmed and shows the not-allowed cursor.

<Slider.Root defaultValue={50} disabled> <Slider.Control> <Slider.Track> <Slider.Indicator /> <Slider.Thumb aria-label="Value" /> </Slider.Track> </Slider.Control> </Slider.Root>

Compound Parts

PartDescription
Slider.RootState container. Manages value, orientation, and disabled state.
Slider.ValueDisplays the current numeric value as text.
Slider.ControlThe interactive area. Handles pointer and keyboard events.
Slider.TrackThe background rail. Full width (or height when vertical).
Slider.IndicatorFills the track from origin to the current thumb position.
Slider.ThumbThe draggable handle. Requires aria-label for accessibility.

Props

All compound parts are thin style wrappers. Props are forwarded to the underlying Base UI Slider. Slider.Root also takes labels:

NameTypeDefault
labelsPartial<SliderLabels>

Replaces the built-in English strings, e.g. to translate them. Keys you leave out keep the default from DEFAULT_SLIDER_LABELS. getAriaValueText and aria-valuetext on a thumb take precedence.

Labels

labels replaces the built-in English text, for example to translate it. Keys you leave out keep their default from DEFAULT_SLIDER_LABELS. They are the aria-valuetext that Base UI gives the two thumbs of a range slider, as functions of the formatted value. getAriaValueText and aria-valuetext on Slider.Thumb take precedence. See Labels.

NameTypeDefault
rangeStart(value: string) => string

The aria-valuetext of the first thumb of a range slider (two values). Gets the formatted value.

(value) => "20 start range"
rangeEnd(value: string) => string

The aria-valuetext of the second thumb of a range slider. Gets the formatted value.

(value) => "80 end range"
Last updated on