Tabs

Tab primitives for switching between related panels.

Quick Preview

Property summary and buyer requirements.

Composition

Use this public composition when building Tabs:

Tabs
├── TabsListContainer (optional)
│   └── TabsList
│       └── TabsTrigger
│           └── TabsCount (optional)
└── TabsContent

Usage

<Tabs defaultValue="overview"><TabsList><TabsTrigger value="overview">Overview</TabsTrigger></TabsList><TabsContent value="overview">Overview</TabsContent></Tabs>

Examples

Variants

Use variant on TabsList to choose underline navigation or pill-style secondary tabs.

Underline tabs work well in page headers.
Secondary tabs work well inside cards and sheets.

Count

Render TabsCount inside a TabsTrigger, after the label, to show a count badge. It picks up the active tab and the current size automatically. Reserve counts for meaningful, changing quantities — unread, pending, errors.

Property summary and buyer requirements.

Bar container

TabsList is the row of tabs. TabsListContainer is the bar it sits in — wrap the list in one when the bar needs padding the tabs shouldn't inherit, or when something other than a tab has to sit in it.

The container owns the underline variant's baseline rule, so the rule spans the whole bar while the tabs stay inset. Without a container TabsList keeps drawing the rule itself, so existing markup is unaffected.

The rule runs the full width of the bar — under the padding and under the filter button — while the tabs stay inset.
<TabsListContainer className="px-4">
  <TabsList>
    <TabsTrigger value="all">All</TabsTrigger>
  </TabsList>
  <Button variant="ghost" size="sm" className="my-auto ml-auto">Filter</Button>
</TabsListContainer>

variant and size stay on TabsList — the container reads the list's variant to decide whether to draw a rule, so a secondary list inside a container can never leave a stray line behind it.

Pad the container along the rule, not across it. The active indicator is pinned to the list's edge — the bottom when horizontal, the right when vertical — so padding on that edge lifts the indicator off the rule. px is safe on a horizontal bar, py on a vertical one.

Sizes

Use size on TabsList to scale the triggers. Defaults to md; sm is compact for dense or in-card contexts, lg for prominent top-level navigation. It also inherits from an ancestor SizeProvider (e.g. inside a Sheet), so tabs match their surrounding surface automatically.

size="sm"
size="md"
size="lg"

Orientation

Use vertical orientation for side navigation inside settings or detail views. The underline variant becomes a rail down the right of the list — the side the content sits on — with the active indicator riding it, mirroring the baseline under a horizontal bar.

Profile completion and buyer details.

Props

Prop/APITypeDefaultDescription
orientation`"horizontal""vertical"`"horizontal"
size on TabsList`"sm""md""lg"`
size on Tabs`"sm""md""lg"`
TabsListContainerdiv element-Optional bar around TabsList; owns the underline rule so padding on the bar doesn't inset it.
variant on TabsList`"default""line""secondary"
nativeButton on TabsTriggerboolean-Uses native button rendering behavior.
TabsCountspan element-Optional count badge; place inside TabsTrigger after the label.
classNamestring-Local layout or spacing overrides.
native/root propsReact component props-Passed through to the underlying root or primitive.

Accessibility

  • Preserve the documented Tabs composition so labels, triggers, content, and controls remain connected.
  • Provide visible labels or accessible names for interactive controls.
  • Preserve the component-provided focus, keyboard, disabled, and invalid-state behavior.
  • Do not communicate state with color alone; include text, icons, or helper copy.

On this page