Step Slider
A slider that snaps to a fixed set of values, from the Notra pricing page.
"use client";
import { useState } from "react";
import { StepSlider } from "../components/step-slider";
const PROMPT_STEPS = [5, 10, 25, 50, 100, 150, 250, 500, 1000] as const;
const THOUSAND = 1000;
const formatPrompts = (value: number) =>
value >= THOUSAND ? `${value / THOUSAND}K` : value;
export default function StepSliderExample() {
const [prompts, setPrompts] = useState(10);
return (
<div className="flex w-full max-w-3xl flex-col gap-5 p-6">
<div className="flex items-baseline justify-between gap-6">
<span className="text-lg font-medium">Prompts</span>
<span className="text-4xl tabular-nums">{prompts}</span>
</div>
<StepSlider
aria-label="Prompts"
formatLabel={formatPrompts}
getValueText={(value) => `${value} prompts`}
majorSteps={[5, 25, 100, 250, 1000]}
onValueChange={setPrompts}
steps={PROMPT_STEPS}
value={prompts}
/>
</div>
);
}
$ bunx --bun shadcn@latest add @notra/step-sliderStepSlider is built on Base UI’s Slider, like the shadcn Slider, so it keeps keyboard, pointer and screen reader support. The values don’t have to be evenly spaced: every stop takes the same room on the track. The purple fill carries a dot texture, and a brighter band of dots sweeps through it on every step, while dragging too. Reduced motion turns the sweep off.
<StepSlider
aria-label="Prompts"
onValueChange={setPrompts}
steps={[5, 10, 25, 50, 100]}
value={prompts}
/>
| Prop | Default | Description |
|---|---|---|
steps |
The values the slider snaps to, in ascending order. | |
value |
The selected value. A value between stops shows as the nearest stop. | |
defaultValue |
first step | The starting value when value is not set. |
onValueChange |
Called with the new value on every step. | |
onValueCommitted |
Called when a drag, key press or label click ends. | |
formatLabel |
the number | Label under each stop. Clicking a label selects it. |
majorSteps |
all steps | Steps whose label stays visible when the slider is narrower than 32rem. |
hideLabels |
false |
Hides the labels under the track. |
getValueText |
the number | Screen reader text for a value, e.g. "10 prompts". |
positionOf |
nearest step | Fractional step index for a value, to place typed values between stops, e.g. 2.5. |
name |
Submits the selected value, not the step index, with a form. |
Every other Base UI Slider.Root prop, such as disabled, is passed through. For right-to-left layouts, wrap the slider in Base UI’s DirectionProvider with direction="rtl" so the thumb flips along with the stops.