Tabs

Switch between panels with a sliding indicator, direction-aware panel transitions and an animated height.

Preview

Usage

import {
  Tabs,
  TabsContent,
  TabsList,
  TabsPanels,
  TabsTrigger,
} from '@vitnode/core/components/ui/tabs'
<Tabs defaultValue="overview">
  <TabsList>
    <TabsTrigger value="overview">Overview</TabsTrigger>
    <TabsTrigger value="activity">Activity</TabsTrigger>
  </TabsList>

  <TabsPanels>
    <TabsContent value="overview">Overview panel</TabsContent>
    <TabsContent value="activity">Activity panel</TabsContent>
  </TabsPanels>
</Tabs>

Motion

Click around the preview. Three things move, on the same easing:

  • The indicator slides and resizes to the active tab. TabsList renders it for you.
  • The panels crossfade and drift in the direction you travelled: pick a tab to the right and the new panel arrives from the right.
  • The panel area animates its height, so the page (or dialog) never jumps.

Under reduced motion, nothing slides or resizes. Panels just crossfade.

TabsPanels is required

TabsPanels measures the panels, animates the height and clips the outgoing panel. Always wrap TabsContent in it. Don't add padding: it carries its own, so focus rings aren't clipped.

Line variant

An underline instead of a filled pill. Same motion.

<TabsList variant="line">

Vertical

Triggers stack beside the panels. The indicator and panels move up and down.

<Tabs defaultValue="general" orientation="vertical">

Keep panels mounted

Inactive panels unmount. In forms, a field on a hidden tab must still submit, so pass keepMounted. Auto Form does this for its tabs.

<TabsContent keepMounted value="overview">

API Reference

Base UI - Tabs