Slider
A Slider is a draggable input that allows a user to select an imprecise numerical value within a range.
const DefaultSliderExample = () => {const [value, setValue] = React.useState(0.75);const id = useUID();const numberFormatter = React.useMemo(() => {return new Intl.NumberFormat('en-US');}, []);return (<Form><FormControl><Label htmlFor={id}>Brightness</Label><Sliderid={id}numberFormatter={numberFormatter}value={value}onChange={(newValue) => setValue(newValue)}/></FormControl></Form>);};render(<DefaultSliderExample />)
A Slider allows a user to select a numerical value when:
- Immediate feedback is important.
- The value doesn’t need to be precise, especially when the act of choosing a bigger or smaller value is more important than the value itself.
- The value is in a defined range.
Slider uses Adobe's Spectrum React-Aria useSlider under the hood.
Both Sliders and number Inputs are form fields that take numerical values. Because the mouse and touch interaction on a Slider is less precise, use a Slider when the exact number value isn’t important, for example, when selecting image opacity or audio volume.
If the user needs to select an exact value, use a number Input instead. If you want to let users select between consecutive values, you can also use a Radio Button Group.
Slider is a form element and follows the same accessibility guidelines as other form fields:
- Include a label on all form fields. Use one of 3 ways to label a form field:
- Visible label with Label (preferred)
- Visible label that's associated to the input with
aria-labelledby
- Label directly using
aria-label
- Each label must use the
htmlFor
prop that equals theid
of the associated Input. - Provide clear identification of required fields in the label or at the start of a form.
Use the
required
prop to programmatically indicate they are required to browsers. - Include inline error Help Text on any field that errors to make it visually clear that the field changed.
- If the input has associated help text, include the
aria-describedby
prop on the input. This should match theid
of the help text.
Use a Slider when a user should select an imprecise value from a midsized and defined numerical range, such as 1–100.
const DefaultSliderExample = () => {const [value, setValue] = React.useState(0.75);const id = useUID();const numberFormatter = React.useMemo(() => {return new Intl.NumberFormat('en-US');}, []);return (<Form><FormControl><Label htmlFor={id}>Brightness</Label><Sliderid={id}numberFormatter={numberFormatter}value={value}onChange={(newValue) => setValue(newValue)}/></FormControl></Form>);};render(<DefaultSliderExample />)
Avoid errors on Sliders by changing the defined range so no errors can occur.
If a user is still able to choose an invalid option, change the Slider to its error state and use Help Text to add an inline error. For additional guidance on how to compose error messages, refer to the error state pattern.
const ErrorSliderExample = () => {const [value, setValue] = React.useState(0.2);const id = useUID();const helpTextId = useUID();const numberFormatter = React.useMemo(() => {return new Intl.NumberFormat('en-US', { style: 'percent' });}, []);const hasError = value < 0.3;return (<Form><FormControl><Label required htmlFor={id}>Delivery alerts</Label><SliderhasError={hasError}id={id}aria-describedby={helpTextId}value={value}minValue={0}maxValue={1}step={0.01}onChange={(newValue) => setValue(newValue)}numberFormatter={numberFormatter}/><HelpText id={helpTextId} variant={hasError ? "error" : "default"}>The delivery rate's threshold must be greater than 30%.</HelpText></FormControl></Form>);};render(<ErrorSliderExample />)
Use a disabled Slider to show users that they can't interact with the Slider.
const DisabledSliderExample = () => {const [value, setValue] = React.useState(0.5);const id = useUID();const numberFormatter = React.useMemo(() => {return new Intl.NumberFormat('en-US', { style: 'percent' });}, []);return (<Form><FormControl><Label disabled htmlFor={id}>Volume</Label><Sliderdisabledid={id}value={value}minValue={0}maxValue={1}step={0.01}onChange={(newValue) => setValue(newValue)}numberFormatter={numberFormatter}/></FormControl></Form>);};render(<DisabledSliderExample />)
Use a custom range Slider when the default range doesn't fit your use case.
const CustomRangeSliderExample = () => {const [value, setValue] = React.useState(0.55);const id = useUID();const PercentFormatter = React.useMemo(() => {return new Intl.NumberFormat('en-US', { style: 'percent' });}, []);return (<Form><FormControl><Label htmlFor={id}>Partition size</Label><Sliderid={id}value={value}minValue={0.5}maxValue={0.8}step={0.01}onChange={(newValue) => setValue(newValue)}numberFormatter={PercentFormatter}/></FormControl></Form>);};render(<CustomRangeSliderExample />)
Use a Slider with hidden range labels when the range is obvious or the labels are not needed.
const HiddenRangeLabelsSlider = () => {const [value, setValue] = React.useState(32);const id = useUID();const NumberFormatter = React.useMemo(() => {return new Intl.NumberFormat('en-US');}, []);return (<Form><FormControl><Label htmlFor={id}>Scale</Label><Sliderid={id}value={value}onChange={(newValue) => setValue(newValue)}numberFormatter={NumberFormatter}hideRangeLabels/></FormControl></Form>);};render(<HiddenRangeLabelsSlider />)
Do
Use a Slider for mid-sized, defined ranges, usually 1–100.
Don't
Don’t use a Slider for very large or very small ranges.
Do
Use a number Input when an exact number value matters.
Don't
Don’t use a Slider when an exact number value matters.
Do
Use a Meter when you need to visually show the size of a numerical value, but don’t want the bar to be interactive.
Don't
Don’t use a disabled Slider when the value of the Slider is important to show. Disabled form fields aren’t high-contrast enough to be visible.
Do
Use a Radio Group or Radio Button Group to allow users to select a list of consecutive options with precision, whether they’re numerical or not.
Don't
Don’t use a Slider to allow selection of non-numerical values or when there isn’t a definable range.