Skip to content

Segmented control

In review
Live · web

View mode: the pill slides; the preview below swaps (Tab in, Arrow keys)

Text only: 2 · 3 · 5 segments

NockerlIcon + label · icon only, sm and md

A disabled segment: skipped by arrow keys, still legible

Full-width: equal-share segments fill the row

Disabled control: dimmed but readable, not interactive

Viewing list · range week · diff unified. The pill slides to the active segment. The island is live.

// Web: React, consuming @dizyx/nockerl-tokens. (Web is the laggard platform;
// this is the canonical API the published @dizyx/nockerl-react package exposes.)
import { NockerlSegmentedControl } from '@dizyx/nockerl-react';
export function TaskViewSwitch() {
const [view, setView] = useState('list');
return (
<>
<NockerlSegmentedControl
label="Task view"
value={view}
onChange={setView}
segments={[
{ value: 'list', label: 'List', icon: 'list' },
{ value: 'grid', label: 'Grid', icon: 'grid' },
{ value: 'board', label: 'Board', icon: 'board' },
]}
/>
{view === 'list' ? <TaskList /> : view === 'grid' ? <TaskGrid /> : <TaskBoard />}
</>
);
}
// NockerlIcon-only, compact: pass `icon` + `title` (the accessible name) and no `label`.
<NockerlSegmentedControl label="Appearance" size="sm" value={theme} onChange={setTheme}
segments={[
{ value: 'light', icon: 'sun', title: 'Light' },
{ value: 'dark', icon: 'moon', title: 'Dark' },
{ value: 'auto', icon: 'auto', title: 'Auto' },
]} />
PropTypeDefaultDescription
segments *Segment[]The segments, left-to-right. 2-5 mutually-exclusive peers.
value *stringThe currently-active value (controlled). Exactly one is selected.
onChange(next: string) => voidFired with the next value. Ignored for a disabled segment.
label *stringAccessible name for the group (wired via aria-label).
sizeSegmentSize'md'Control height + padding + type role.
orientation'horizontal' | 'vertical''horizontal'Track axis. horizontal (default) = segments in a row, pill slides X. vertical = segments stacked, pill slides Y (e.g. an AM/PM meridiem in a narrow slot). Additive: omitting it is a no-op for existing (horizontal) consumers.
fullWidthbooleanfalseStretch to fill the row (equal-width segments) vs. hug its content.
disabledbooleanfalseDim + disable the whole control.

Also accepts the native <div> attributes (e.g. onClick, disabled, id, aria-*, data-*), forwarded straight through, plus a forwarded ref.