---
title: Tabs
description:
  A Tabs component built with Radix UI, with additional features such as
  persistent and shared value.
preview: tabs
---

import { UrlBar, WithoutValueTest } from './tabs.client';

## Usage

Import it in your MDX documents.

```mdx
import { Tab, Tabs } from 'fumadocs-ui/components/tabs';

<Tabs items={['Javascript', 'Rust']}>
  <Tab value="Javascript">Javascript is weird</Tab>
  <Tab value="Rust">Rust is fast</Tab>
</Tabs>
```

### Without `value`

Without a `value`, it detects from the children index. Note that it might cause errors on re-renders, it's not encouraged if the tabs might change.

```mdx
import { Tab, Tabs } from 'fumadocs-ui/components/tabs';

<Tabs items={['Javascript', 'Rust']}>
  <Tab>Javascript is weird</Tab>
  <Tab>Rust is fast</Tab>
</Tabs>
```

#### Demo with Re-renders

<Tabs items={['Javascript', 'Rust']}>
  <Tab>Javascript is weird</Tab>
  <Tab>Rust is fast</Tab>
</Tabs>

<WithoutValueTest />

### Shared Value

By passing an `id` property, you can share a value across all tabs with the same
id.

```mdx
<Tabs groupId="language" items={['Javascript', 'Rust']}>
  <Tab value="Javascript">Javascript is weird</Tab>
  <Tab value="Rust">Rust is fast</Tab>
</Tabs>
```

### Persistent

You can enable persistent by passing a `persist` property. The value will be
stored in `localStorage`, with its id as the key.

```mdx
<Tabs groupId="language" items={['Javascript', 'Rust']} persist>
  <Tab value="Javascript">Javascript is weird</Tab>
  <Tab value="Rust">Rust is fast</Tab>
</Tabs>
```

> Persistent only works if you have passed an `id`.

### Default Value

Set a default value by passing `defaultIndex`.

```mdx
<Tabs items={['Javascript', 'Rust']} defaultIndex={1}>
  <Tab value="Javascript">Javascript is weird</Tab>
  <Tab value="Rust">Rust is fast</Tab>
</Tabs>
```

### Link to Tab

Use HTML `id` attribute to link to a specific tab.

```mdx
<Tabs items={['Javascript', 'Rust', 'C++']}>
  <Tab value="Javascript">Javascript is weird</Tab>
  <Tab value="Rust">Rust is fast</Tab>
  <Tab id="tab-cpp" value="C++">
    `Hello World`
  </Tab>
</Tabs>
```

You can add the hash `#tab-cpp` to your URL and reload, the C++ tab will be activated.

<Tabs items={['Javascript', 'Rust', 'C++']}>
  <Tab value="Javascript">Javascript is weird</Tab>
  <Tab value="Rust">Rust is fast</Tab>
  <Tab id="tab-cpp" value="C++">
    `Hello World`
  </Tab>
</Tabs>

Additionally, the `updateAnchor` property can be set to `true` in the `Tabs` component
to automatically update the URL hash whenever time a new tab is selected:

```mdx
<Tabs items={['Javascript', 'Rust', 'C++']} updateAnchor>
  <Tab id="tab-js" value="Javascript">
    Javascript is weird
  </Tab>
  <Tab id="tab-rs" value="Rust">
    Rust is fast
  </Tab>
  <Tab id="tab-cpp" value="C++">
    `Hello World`
  </Tab>
</Tabs>
```

<UrlBar />

<Tabs items={['Hello', 'World']} updateAnchor>
  <Tab id="tab-hello" value="Hello">
    Hello!
  </Tab>
  <Tab id="tab-world" value="World">
    World!
  </Tab>
</Tabs>

### Advanced

You can use the styled Radix UI primitive directly from exported `Primitive`.

```mdx
import { Primitive } from 'fumadocs-ui/components/tabs';

<Primitive.Tabs>
  <Primitive.TabsList>
    <Primitive.TabsTrigger />
  </Primitive.TabsList>
  <Primitive.TabsContent />
</Primitive.Tabs>
```
