Examples
Interactive tab bars. Click a tab to switch the active state. All examples include hover, active, and disabled states.
Basic tab bar
Four B2B navigation tabs. Click any tab to activate it.
With icons
16×16 icons before each label reinforce meaning. Use icons consistently — all or none.
Small size (36px)
Compact tabs for secondary navigation or nested contexts.
Medium size (44px)
Default size — suitable for most primary navigation contexts.
With disabled tab
Mark a tab as disabled when its content is unavailable. The tab remains visible but is not interactive.
In context — with content panel
Tab bar linked to a content area below it. Click tabs to switch the displayed content.
Products
Manage your product catalogue — add, edit, and organise SKUs. Set pricing, upload images, and control inventory levels across all warehouses.
Overflow — many tabs
When tabs exceed the container width they overflow horizontally. Consider switching to a side nav or segmented control for 7+ tabs.
Anatomy
① Container
Full-width flex row with 1px bottom border
② Tab item
Clickable hit area — 44px (md) or 36px (sm) tall
③ Icon
Optional 16×16 — use lucide-react or any SVG icon
④ Label
1–2 words, sentence case, always present
⑤ Active indicator
2px brand-700 bottom border on the active tab
States
Small (36px)
Medium (44px)
Design tokens
| Token | Value | Description |
|---|---|---|
background/brand/primary | #318272 | Active indicator color and active tab text |
text/brand | #0f766e | Active tab text color |
text/secondary | #71717a | Default tab text |
text/disabled | #a1a1aa | Disabled tab text |
border/default | #e4e4e7 | Tab bar bottom border |
background/subtle | #f4f4f5 | Hover fill background |
stroke/sm | 2px | Active indicator thickness |
scale/12 | 12px | SM horizontal padding |
scale/16 | 16px | MD horizontal padding |
Props
| Prop | Type | Default | Description |
|---|---|---|---|
tabs | Array<{label: string, icon?: ReactNode, disabled?: boolean}> | — | Array of tab definitions. |
size | "sm" | "md" | "md" | Tab height — 36px (sm) or 44px (md). |
defaultTab | number | 0 | Index of the initially active tab. |
onChange | (index: number) => void | — | Called when the active tab changes. |
className | string | — | Additional CSS classes for the container. |
Content guidelines
Do
- Use 2–7 tabs. Fewer than 2 is pointless; more than 7 is confusing.
- Keep labels to 1–2 words in sentence case.
- Always have exactly one tab active at a time.
- Use icons consistently — all tabs with icons or none.
- Keep tab content related — the same entity viewed in different ways.
Don't
- ✕Don't use tabs for page navigation — use links or a nav component.
- ✕Don't use more than 7 tabs — switch to a side nav.
- ✕Don't mix icon and non-icon tabs in the same bar.
- ✕Don't use tabs to show a sequential workflow — use a stepper.
- ✕Don't make tab content too different in scope from each other.