Navigation · Tabs

Tabs

When the content needs to be grouped and displayed in different modules or pages, you could use Tabs to switch between different groups or pages

Demos

How to import

<script setup lang="ts">
    import { Tabs, TabPane } from '@fibrous/semi-ui-vue';
</script>

Basic Usage

Tabs supports four types of styles: line, button, card, and slash. By default, the first enabled tab is selected.

Tabs supports two declare ways, and the rendering process of the two is different:

  • Pass the array of objects through tabList, when using tabList, only render the currently passed node each time
  • Or use <TabPane> to explicitly pass in item by item. When using <TabPane>, all panels will be rendered by default. You can set keepDOM to false to only render the current panel, and there will be no animation effect at this time.

In Vue the text of a tab goes in the #tab slot of <TabPane> and its icon in the #icon slot. The items of tabList hold data only (itemKey, tab, disabled, closable); for markup use the #tab and #icon scoped slots of Tabs, which receive { item, index }. Without a slot the tab text of the item is shown. Any array, even an empty one, makes the default slot the content of the active tab instead of TabPanes.

文档

Semi Design 是由抖音前端团队与 UED 团队共同设计开发并维护的设计系统。设计系统包含设计语言以及一整套可复用的前端组件,帮助设计师与开发者更容易地打造高质量的、用户体验一致的、符合设计规范的 Web 应用。

区别于其他的设计系统而言,Semi Design 以用户中心、内容优先、设计人性化为设计理念,具有以下优势:

  • Semi Design 以内容优先进行设计。

  • 更容易地自定义主题。

  • 适用国际化场景。

  • 效率场景加入人性化关怀。

Code
<script setup lang="ts">
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const paragraphStyle = { lineHeight: 1.8 };
    const questionStyle = { lineHeight: 1.8, color: 'var(--semi-color-text-0)', fontWeight: 600 };
    const answerStyle = { lineHeight: 1.8, color: 'var(--semi-color-text-1)' };
    const codeStyle = {
        margin: '24px 0',
        padding: '20px',
        border: 'none',
        whiteSpace: 'normal',
        borderRadius: 'var(--semi-border-radius-medium)',
        color: 'var(--semi-color-text-1)',
        backgroundColor: 'var(--semi-color-fill-0)',
    };
</script>

<template>
    <div>
        <Tabs type="line">
            <TabPane itemKey="1">
                <template #tab>文档</template>
                <h3>文档</h3>
                <p :style="paragraphStyle">Semi Design 是由抖音前端团队与 UED 团队共同设计开发并维护的设计系统。设计系统包含设计语言以及一整套可复用的前端组件,帮助设计师与开发者更容易地打造高质量的、用户体验一致的、符合设计规范的 Web 应用。</p>
                <p :style="paragraphStyle">区别于其他的设计系统而言,Semi Design 以用户中心、内容优先、设计人性化为设计理念,具有以下优势:</p>
                <ul>
                    <li>
                        <p>Semi Design 以内容优先进行设计。</p>
                    </li>
                    <li>
                        <p>更容易地自定义主题。</p>
                    </li>
                    <li>
                        <p>适用国际化场景。</p>
                    </li>
                    <li>
                        <p>效率场景加入人性化关怀。</p>
                    </li>
                </ul>
            </TabPane>
            <TabPane itemKey="2">
                <template #tab>快速起步</template>
                <h3>快速起步</h3>
                <pre :style="codeStyle"><code>yarn add @fibrous/semi-ui-vue</code></pre>
            </TabPane>
            <TabPane itemKey="3">
                <template #tab>帮助</template>
                <h3>帮助</h3>
                <p :style="questionStyle">Q:有新组件需求、或者现有组件feature不能满足业务需求?</p>
                <p :style="answerStyle">右上角问题反馈,提交issue,label选择Feature Request / New Component Request 我们会高优处理这些需求。</p>
                <p :style="questionStyle">Q:对组件的使用有疑惑?</p>
                <p :style="answerStyle">欢迎进我们的客服lark群进行咨询提问。</p>
            </TabPane>
        </Tabs>
    </div>
</template>
文档
Code
<script setup lang="ts">
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';
</script>

<template>
    <Tabs type="button">
        <TabPane itemKey="1">
            <template #tab>文档</template>
            文档
        </TabPane>
        <TabPane itemKey="2">
            <template #tab>快速起步</template>
            快速起步
        </TabPane>
        <TabPane itemKey="3">
            <template #tab>帮助</template>
            帮助
        </TabPane>
    </Tabs>
</template>
文档
Code
<script setup lang="ts">
    import { ref } from 'vue';
    import { Tabs } from '@fibrous/semi-ui-vue';

    const contentList = ['文档', '快速起步', '帮助'];
    const tabList = [
        { tab: '文档', itemKey: '1' },
        { tab: '快速起步', itemKey: '2' },
        { tab: '帮助', itemKey: '3' },
    ];
    const key = ref('1');
</script>

<template>
    <Tabs v-model:activeKey="key" :tabList="tabList" type="card">
        <div>{{ contentList[Number(key) - 1] }}</div>
    </Tabs>
</template>
文档
Code
<script setup lang="ts">
    import { ref } from 'vue';
    import { Tabs } from '@fibrous/semi-ui-vue';

    const contentList = ['文档', '快速起步', '帮助'];
    const tabList = [
        { tab: '文档', itemKey: '1' },
        { tab: '快速起步', itemKey: '2' },
        { tab: '帮助', itemKey: '3' },
    ];
    const key = ref('1');
</script>

<template>
    <Tabs v-model:activeKey="key" :tabList="tabList" type="slash">
        <div>{{ contentList[Number(key) - 1] }}</div>
    </Tabs>
</template>

With Icon

文档
Code
<script setup lang="ts">
    import { IconFile, IconGlobe, IconHelpCircle } from '@fibrous/semi-icons-vue';
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';
</script>

<template>
    <Tabs>
        <TabPane itemKey="1">
            <template #tab>
                <span><IconFile />文档</span>
            </template>
            文档
        </TabPane>
        <TabPane itemKey="2">
            <template #tab>
                <span><IconGlobe />快速起步</span>
            </template>
            快速起步
        </TabPane>
        <TabPane itemKey="3">
            <template #tab>
                <span><IconHelpCircle />帮助</span>
            </template>
            帮助
        </TabPane>
    </Tabs>
</template>

More with Dropdown

Supports merging redundant tabs into a more drop-down menu. Just pass in a number for more. The number represents the number of tabs included in the drop-down menu.

Content of card tab 0
Code
<script setup lang="ts">
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const indexes = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
</script>

<template>
    <Tabs :more="4" :style="{ width: '60%', margin: '20px' }" type="card">
        <TabPane v-for="i in indexes" :key="i" :itemKey="`Tab-${i}`">
            <template #tab>Tab-{{ i }}</template>
            Content of card tab {{ i }}
        </TabPane>
    </Tabs>
</template>

Advanced configuration is also supported, passing the object to more, and it can be passed in

  • count: Represents the number of Tabs in the income drop-down menu
  • dropdownProps: Dropdown props, passed through to the drop-down menu

Customize the "More" trigger with the #more slot, and the content of the drop-down menu with the #moreContent="{ items }" scoped slot, where items are the tabs moved into the menu.

Content of card tab 0
Code
<script setup lang="ts">
    import { Button, TabPane, Tabs, type TabsMore } from '@fibrous/semi-ui-vue';

    const indexes = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
    const more: TabsMore = { count: 4, dropdownProps: { trigger: 'click', position: 'bottomRight' } };
</script>

<template>
    <Tabs :more="more" :style="{ width: '60%', margin: '20px' }" type="card">
        <template #more>
            <Button type="tertiary">Click to show More</Button>
        </template>
        <TabPane v-for="i in indexes" :key="i" :itemKey="`Tab-${i}`">
            <template #tab>Tab-{{ i }}</template>
            Content of card tab {{ i }}
        </TabPane>
    </Tabs>
</template>

Vertical mode

When type is line, card, or button, horizontal and vertical modes are supported, tabPosition='left|top',default is top. When type is slash, only horizontal mode is supported.



文档

Semi Design 是由抖音前端团队与 UED 团队共同设计开发并维护的设计系统。设计系统包含设计语言以及一整套可复用的前端组件,帮助设计师与开发者更容易地打造高质量的、用户体验一致的、符合设计规范的 Web 应用。

区别于其他的设计系统而言,Semi Design 以用户中心、内容优先、设计人性化为设计理念,具有以下优势:

Code
<script setup lang="ts">
    import { ref } from 'vue';
    import { IconFile, IconGlobe, IconHelpCircle } from '@fibrous/semi-icons-vue';
    import { Radio, RadioGroup, TabPane, Tabs, type RadioValue, type TabType } from '@fibrous/semi-ui-vue';

    const type = ref<RadioValue | undefined>('line');
    const contentStyle = { padding: '0 24px' };
    const paragraphStyle = { lineHeight: 1.8 };
    const questionStyle = { lineHeight: 1.8, color: 'var(--semi-color-text-0)', fontWeight: 600 };
    const answerStyle = { lineHeight: 1.8, color: 'var(--semi-color-text-1)' };
    const codeStyle = {
        margin: '24px 0',
        padding: '20px',
        border: 'none',
        whiteSpace: 'normal',
        borderRadius: '6px',
        color: 'var(--semi-color-text-1)',
        backgroundColor: 'var(--semi-color-fill-0)',
    };
</script>

<template>
    <RadioGroup v-model="type" :style="{ display: 'flex', width: '200px', justifyContent: 'center' }" type="button">
        <Radio value="line">Line</Radio>
        <Radio value="card">Card</Radio>
        <Radio value="button">Button</Radio>
    </RadioGroup>
    <br />
    <br />
    <Tabs tabPosition="left" :type="type as TabType">
        <TabPane itemKey="1">
            <template #tab>
                <span><IconFile />文档</span>
            </template>
            <div :style="contentStyle">
                <h3>文档</h3>
                <p :style="paragraphStyle">Semi Design 是由抖音前端团队与 UED 团队共同设计开发并维护的设计系统。设计系统包含设计语言以及一整套可复用的前端组件,帮助设计师与开发者更容易地打造高质量的、用户体验一致的、符合设计规范的 Web 应用。</p>
                <p :style="paragraphStyle">区别于其他的设计系统而言,Semi Design 以用户中心、内容优先、设计人性化为设计理念,具有以下优势:</p>
            </div>
        </TabPane>
        <TabPane itemKey="2">
            <template #tab>
                <span><IconGlobe />快速起步</span>
            </template>
            <div :style="contentStyle">
                <h3>快速起步</h3>
                <pre :style="codeStyle"><code>yarn add @fibrous/semi-ui-vue</code></pre>
            </div>
        </TabPane>
        <TabPane itemKey="3">
            <template #tab>
                <span><IconHelpCircle />帮助</span>
            </template>
            <div :style="contentStyle">
                <h3>帮助</h3>
                <p :style="questionStyle">Q:有新组件需求、或者现有组件feature不能满足业务需求?</p>
                <p :style="answerStyle">右上角问题反馈,提交issue,label选择Feature Request / New Component Request 我们会高优处理这些需求。</p>
                <p :style="questionStyle">Q:对组件的使用有疑惑?</p>
                <p :style="answerStyle">欢迎进我们的客服lark群进行咨询提问。</p>
            </div>
        </TabPane>
    </Tabs>
</template>

Scrollable Tabs

You could use collapsible for a scrollable tabs with dropdown menu. Horizontal mode only.

Content of card tab 0
Code
<script setup lang="ts">
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const indexes = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
</script>

<template>
    <Tabs collapsible :style="{ width: '60%', margin: '20px' }" type="card">
        <TabPane v-for="i in indexes" :key="i" :itemKey="`Tab-${i}`">
            <template #tab>Tab-{{ i }}</template>
            Content of card tab {{ i }}
        </TabPane>
    </Tabs>
</template>

Modify the scrolling rendering Arrow

The #arrow scoped slot modifies the arrows in collapsible mode. It receives the overflowed items, the position, the click function onClick and the default arrow defaultNode (render it with <component :is="defaultNode" />).

Content of card tab 0
Code
<script setup lang="ts">
    import { ref } from 'vue';
    import { Dropdown, TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const activeKey = ref('Tab-0');
    const indexes = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
    const arrowStyle = {
        width: '32px',
        height: '32px',
        margin: '0 12px',
        display: 'flex',
        justifyContent: 'center',
        alignItems: 'center',
        padding: '0',
        border: 'none',
        borderRadius: '100%',
        background: 'var(--semi-grey-1)',
        color: 'var(--semi-color-text)',
        fontFamily: 'inherit',
        fontSize: 'inherit',
        cursor: 'pointer',
    };
</script>

<template>
    <Tabs v-model:activeKey="activeKey" collapsible :style="{ width: '50%', margin: '20px' }" type="card">
        <template #arrow="{ items, position, onClick }">
            <Dropdown>
                <button :style="arrowStyle" type="button" @click="onClick">
                    {{ position === 'start' ? '←' : '→' }}
                </button>
                <template #content>
                    <Dropdown.Menu>
                        <Dropdown.Item v-for="item in items" :key="item.itemKey" @click="activeKey = item.itemKey">
                            {{ item.itemKey }}
                        </Dropdown.Item>
                    </Dropdown.Menu>
                </template>
            </Dropdown>
        </template>
        <TabPane v-for="i in indexes" :key="i" :itemKey="`Tab-${i}`">
            <template #tab>Tab-{{ i }}</template>
            Content of card tab {{ i }}
        </TabPane>
    </Tabs>
</template>

Modify Arrow rendering position

Use arrowPosition to modify the overflow indicator position, optional start both end

Content of card tab 0
Content of card tab 0
Content of card tab 0
Code
<script setup lang="ts">
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const positions = ['start', 'both', 'end'] as const;
    const indexes = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
</script>

<template>
    <Tabs v-for="position in positions" :key="position" :arrowPosition="position" collapsible :style="{ width: '60%', margin: '20px' }" type="card">
        <TabPane v-for="i in indexes" :key="i" :itemKey="`Tab-${i}`">
            <template #tab>Tab-{{ i }}</template>
            Content of card tab {{ i }}
        </TabPane>
    </Tabs>
</template>

Auto Overflow Detection

Set collapsible="auto" to enable automatic overflow detection. The component will automatically detect whether tabs overflow the container:

  • When tabs exceed the container width or wrap to multiple lines, it automatically enables collapse mode (shows left/right arrows)
  • When the container width increases or tab count decreases and all tabs can be fully displayed, it automatically exits collapse mode

This feature eliminates the need for developers to manually determine whether folding is needed, making it especially suitable for responsive layouts.

当前 Tab 数量: 8

collapsible="auto" - 自动检测溢出

Content of Tab 1

固定宽度 400px,测试较窄容器

Content of Tab 1
Code
<script setup lang="ts">
    import { computed, ref } from 'vue';
    import { Button, TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const count = ref(8);
    const indexes = computed(() => Array.from({ length: count.value }, (_, i) => i));

    const boxStyle = { border: '1px solid var(--semi-color-border)', padding: '12px' };
    const noteStyle = { marginBottom: '8px', color: 'var(--semi-color-text-2)', fontSize: '12px' };
</script>

<template>
    <div>
        <div :style="{ marginBottom: '12px' }">
            <Button :style="{ marginRight: '8px' }" @click="count = Math.max(3, count - 2)">减少 Tab</Button>
            <Button @click="count = Math.min(15, count + 2)">增加 Tab</Button>
            <span :style="{ marginLeft: '12px' }">当前 Tab 数量: {{ count }}</span>
        </div>

        <div :style="{ ...boxStyle, marginBottom: '16px' }">
            <p :style="noteStyle">collapsible="auto" - 自动检测溢出</p>
            <Tabs collapsible="auto" type="card">
                <TabPane v-for="i in indexes" :key="i" :itemKey="`${i}`">
                    <template #tab>Tab-{{ i + 1 }}</template>
                    Content of Tab {{ i + 1 }}
                </TabPane>
            </Tabs>
        </div>

        <div :style="{ ...boxStyle, maxWidth: '400px' }">
            <p :style="noteStyle">固定宽度 400px,测试较窄容器</p>
            <Tabs collapsible="auto" type="card">
                <TabPane v-for="i in indexes" :key="i" :itemKey="`${i}`">
                    <template #tab>Tab-{{ i + 1 }}</template>
                    Content of Tab {{ i + 1 }}
                </TabPane>
            </Tabs>
        </div>
    </div>
</template>

Disable

Disable one tab.

文档
Code
<script setup lang="ts">
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';
</script>

<template>
    <Tabs defaultActiveKey="1">
        <TabPane itemKey="1">
            <template #tab>文档</template>
            文档
        </TabPane>
        <TabPane disabled itemKey="2">
            <template #tab>快速起步</template>
            快速起步
        </TabPane>
        <TabPane itemKey="3">
            <template #tab>帮助</template>
            帮助
        </TabPane>
    </Tabs>
</template>

Extra Content

Use the #tabBarExtraContent slot to add extra content on the right side of tabBar.

文档
Code
<script setup lang="ts">
    import { Button, TabPane, Tabs } from '@fibrous/semi-ui-vue';

    function onExtraClick() {
        alert('you have clicked me!');
    }
</script>

<template>
    <Tabs defaultActiveKey="1">
        <template #tabBarExtraContent>
            <Button @click="onExtraClick">Extra Action</Button>
        </template>
        <TabPane itemKey="1">
            <template #tab>文档</template>
            文档
        </TabPane>
        <TabPane itemKey="2">
            <template #tab>快速起步</template>
            快速起步
        </TabPane>
        <TabPane itemKey="3">
            <template #tab>帮助</template>
            帮助
        </TabPane>
    </Tabs>
</template>

Custom Render

Use the #tabBar="{ tabBarProps, tabBar }" scoped slot to customize the tab bar. tabBarProps holds data only (see TabBarProps below) and tabBar is the default tab bar node, rendered with <component :is="tabBar" />.

When #tabBar replaces the bar entirely, the aria-label and aria-labelledby of Tabs do not reach your own element: put the accessible name on your own role="tablist" element. The entries of tabBarProps.list carry the tab text only when the #tab slot of the TabPane is plain text.

这是二次封装的Tab Bar,当前ActiveKey:1
文档
Code
<script setup lang="ts">
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';
</script>

<template>
    <Tabs defaultActiveKey="1">
        <template #tabBar="{ tabBarProps, tabBar }">
            <div class="tab-bar-box">
                这是二次封装的Tab Bar,当前ActiveKey:{{ tabBarProps.activeKey }}
                <component :is="tabBar" />
            </div>
        </template>
        <TabPane itemKey="1">
            <template #tab>文档</template>
            文档
        </TabPane>
        <TabPane itemKey="2">
            <template #tab>快速起步</template>
            快速起步
        </TabPane>
        <TabPane itemKey="3">
            <template #tab>帮助</template>
            帮助
        </TabPane>
    </Tabs>
</template>

Drag and Drop Reordering

Through the #tabBar slot, render the tabs with TabItem inside your own role="tablist" element and combine them with dragging to reorder the tab bar. Inside a Tabs a TabItem selects its tab on click by itself, and native attributes and listeners such as draggable and the drag events land on its root element. The demo uses native browser drag and drop, which supports pointer input only; when you need keyboard sorting, use a drag library with keyboard support such as @dnd-kit/dom instead.

文档内容
Code
<script setup lang="ts">
    import { ref } from 'vue';
    import { TabItem, TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const activeKey = ref('1');
    const items = ref([
        { itemKey: '1', tab: '文档', content: '文档内容' },
        { itemKey: '2', tab: '表格', content: '表格内容' },
        { itemKey: '3', tab: '幻灯片', content: '幻灯片内容' },
        { itemKey: '4', tab: '表单', content: '表单内容' },
    ]);

    // HTML5 drag and drop on the TabItems: the website has no @dnd-kit/vue, and a Vue sortable list would wrap each tab
    // in a button-role element that nests focusable tabs. Known limit: pointer only; use dnd-kit for keyboard sorting.
    const draggingKey = ref<string | null>(null);
    const moveTo = (targetKey: string) => {
        const from = items.value.findIndex((item) => item.itemKey === draggingKey.value);
        const to = items.value.findIndex((item) => item.itemKey === targetKey);
        if (from < 0 || to < 0 || from === to) return;
        const [moved] = items.value.splice(from, 1);
        items.value.splice(to, 0, moved);
    };
</script>

<template>
    <Tabs v-model:activeKey="activeKey" type="line">
        <!-- the bar keeps Semi's own .semi-tabs-bar shell; the TabItems inside select their Tabs by themselves -->
        <template #tabBar>
            <div aria-orientation="horizontal" class="semi-tabs-bar semi-tabs-bar-line semi-tabs-bar-top" role="tablist">
                <TabItem
                    v-for="item in items"
                    :key="item.itemKey"
                    draggable="true"
                    :itemKey="item.itemKey"
                    :selected="activeKey === item.itemKey"
                    :style="{ cursor: 'grab', opacity: draggingKey === item.itemKey ? 0.5 : 1, display: 'inline-flex' }"
                    @dragend="draggingKey = null"
                    @dragenter.prevent="moveTo(item.itemKey)"
                    @dragover.prevent
                    @dragstart="draggingKey = item.itemKey"
                >
                    <template #tab>{{ item.tab }}</template>
                </TabItem>
            </div>
        </template>
        <TabPane v-for="item in items" :key="item.itemKey" :itemKey="item.itemKey">
            <div :style="{ padding: '20px' }">{{ item.content }}</div>
        </TabPane>
    </Tabs>
</template>

Dynamic Update

You can add events to update tabBar dynamically.

Content of Tab Pane 1
Code
<script setup lang="ts">
    import { ref } from 'vue';
    import { Button, ButtonGroup, TabPane, Tabs } from '@fibrous/semi-ui-vue';

    let newTabIndex = 0;
    const panes = ref([
        { title: 'Tab 1', content: 'Content of Tab Pane 1', itemKey: '1' },
        { title: 'Tab 2', content: 'Content of Tab Pane 2', itemKey: '2' },
    ]);
    const activeKey = ref('1');

    const add = () => {
        const index = newTabIndex++;
        panes.value.push({ title: `New Tab ${index}`, content: 'New Tab Pane', itemKey: `newTab${index}` });
        activeKey.value = `newTab${index}`;
    };

    const remove = () => {
        if (panes.value.length > 1) {
            panes.value.pop();
            activeKey.value = panes.value[panes.value.length - 1].itemKey;
        }
    };
</script>

<template>
    <Tabs v-model:activeKey="activeKey">
        <template #tabBarExtraContent>
            <ButtonGroup>
                <Button @click="add">新增</Button>
                <Button @click="remove">删除</Button>
            </ButtonGroup>
        </template>
        <TabPane v-for="pane in panes" :key="pane.itemKey" :itemKey="pane.itemKey">
            <template #tab>{{ pane.title }}</template>
            {{ pane.content }}
        </TabPane>
    </Tabs>
</template>

Closeable

Close a tab in the tab bar. All four tab styles support the close option; set closable on the tab to turn it on. A disabled tab cannot be closed. The caller removes the tab in the close callback.

文档
Code
<script setup lang="ts">
    import { ref } from 'vue';
    import { TabPane, Tabs } from '@fibrous/semi-ui-vue';

    const tabList = ref([
        { tab: '文档', itemKey: '1', text: '文档', closable: true },
        { tab: '快速起步', itemKey: '2', text: '快速起步', closable: true },
        { tab: '帮助', itemKey: '3', text: '帮助', closable: false },
    ]);

    const close = (key: string) => {
        tabList.value = tabList.value.filter((t) => t.itemKey !== key);
    };
</script>

<template>
    <Tabs defaultActiveKey="1" type="card" @tabClose="close">
        <TabPane v-for="t in tabList" :key="t.itemKey" :closable="t.closable" :itemKey="t.itemKey">
            <template #tab>{{ t.tab }}</template>
            {{ t.text }}
        </TabPane>
    </Tabs>
</template>

API Reference

Tab

Props

PropertyDescriptionTypeDefault
activeKeyThe itemKey of the active tab, used with v-model:activeKey. null activates no tab and is still controlled; omitted or undefined means uncontrolled.string | nullsemiGlobalDefault("Tabs", "activeKey")
arrowPositionPosition of the scroll arrows in collapsible mode."both" | "start" | "end"semiDefault("Tabs", "arrowPosition", "both")
collapsibleWhether to collapse overflowing tabs into a scrollable bar (horizontal mode only). 'auto' collapses when the tabs overflow or wrap and leaves the collapse once they fit.boolean | "auto"semiDefault("Tabs", "collapsible", false)
contentStyleStyle of the outer content area.StyleValuesemiGlobalDefault("Tabs", "contentStyle")
defaultActiveKeyThe itemKey selected initially when uncontrolled. Defaults to the first enabled tab that has an itemKey.stringsemiGlobalDefault("Tabs", "defaultActiveKey")
dropdownPropsIn collapsible mode, the Dropdown props passed to the start-side and end-side arrow menus.TabsDropdownPropssemiGlobalDefault("Tabs", "dropdownProps")
keepDOMWith TabPane children, whether to render the DOM of inactive panels. When false only the active panel is rendered, without motion.booleansemiDefault("Tabs", "keepDOM", true)
lazyRenderLazy rendering: a panel is rendered into the DOM only after it has been active.booleansemiDefault("Tabs", "lazyRender", false)
moreMoves the last tabs into a More dropdown. A number is the count of tabs moved; in an object, count is that number and dropdownProps is passed to the dropdown. The trigger and the menu content are customized with the more and moreContent slots.number | TabsMoresemiGlobalDefault("Tabs", "more")
preventScrollWhether focus calls inside the component stop the browser from scrolling the document to the newly focused element.booleansemiGlobalDefault("Tabs", "preventScroll")
showRestInDropdownIn collapsible mode, whether the collapsed tabs are listed in a dropdown menu.booleansemiDefault("Tabs", "showRestInDropdown", true)
sizeSize of the tab bar; currently only the line type supports it.TabSizesemiDefault("Tabs", "size", "large")
tabBarClassNameClass name of the tab bar.stringsemiGlobalDefault("Tabs", "tabBarClassName")
tabBarStyleStyle of the tab bar.StyleValuesemiGlobalDefault("Tabs", "tabBarStyle")
tabListAn array of tab data, each with itemKey, tab, disabled and closable. Any array, even an empty one, makes the default slot the content of the active tab and takes precedence over TabPane children; tab markup goes in the tab and icon slots.PlainTab[]semiGlobalDefault("Tabs", "tabList")
tabPaneMotionWhether switching panels is animated.booleansemiDefault("Tabs", "tabPaneMotion", true)
tabPositionPosition of the tab bar: top is horizontal, left is vertical.TabPositionsemiDefault("Tabs", "tabPosition", "top")
typeStyle of the tab bar: line, card, button or slash. slash supports horizontal mode only.TabTypesemiDefault("Tabs", "type", "line")
visibleTabsStyleIn collapsible mode, the style of the whole scrolling area.StyleValuesemiGlobalDefault("Tabs", "visibleTabsStyle")

Events

EventDescriptionCallback parameters
update:activeKeyEmitted when the active tab changes, for v-model:activeKey to write back.[activeKey: string]
changeEmitted when the tab changes, with the itemKey of the new active tab; emitted together with update:activeKey.[activeKey: string]
tabClickEmitted when a tab is clicked or activated with Enter or Space; the event is a KeyboardEvent for keyboard activation.[activeKey: string, event: MouseEvent | KeyboardEvent]
tabCloseEmitted when a tab is closed, with the itemKey of the closed tab. The caller removes the tab.[tabKey: string]
visibleTabsChangeIn collapsible mode, emitted when the visibility of the tabs changes, with a Map from itemKey to whether it is visible.Type[visibleState: Map<string, boolean>]

Slots

SlotDescriptionScope parameters
defaultTabPane children; with tabList, the content of the active tab. TabPane must be a direct child of Tabs.any
tabThe tab of each tabList entry, with item and index; without it the entry's tab text shows.TabsTabSlotProps
iconThe icon of each tabList entry, with item and index; an empty result renders no icon.TabsTabSlotProps
tabBarExtraContentExtra content of the tab bar, placed outside the tablist.any
tabBarReplaces the whole tab bar. tabBarProps holds data only and tabBar is the default tab bar node, rendered with component :is; a TabItem inside the custom bar controls its Tabs on its own.TabsTabBarSlotProps
arrowReplaces each scroll arrow in collapsible mode, with the scrolled-out items, position, onClick and the default arrow defaultNode.TabsArrowSlotProps
moreReplaces the trigger of the More menu.any
moreContentReplaces the content of the More menu, with the tabs moved into it as items.TabsMoreContentSlotProps

Exposes

NameDescriptionType
None

activeKey is used with v-model:activeKey. aria-label and aria-labelledby land on the role="tablist" element; class, style and other native attributes land on the root element.

PlainTab

The data item of tabList; it holds data only.

PropertyDescriptionTypeDefault Value
itemKeyUnique key of the tab, matched against activeKeystringNone
tabTab text; the #tab slot takes precedencestring | numberNone
disabledWhether the tab is disabledbooleanNone
closableWhether the tab can be closedbooleanNone

TabsMore

The shape of more when it is an object.

PropertyDescriptionTypeDefault Value
countNumber of Tabs moved into the drop-down menunumberNone
dropdownPropsDropdown props passed through to the menuTabsDropdownItemPropsNone

TabsDropdownItemProps is the props of Dropdown plus class, style and onVisibleChange. The start and end of dropdownProps use the same type.

TabBarProps

The tabBarProps of the #tabBar slot, the data of the default tab bar.

PropertyDescriptionType
activeKeyThe active itemKey; null for a controlled empty valuestring | null
listTab data; tab is present only when the #tab of a TabPane is plain textPlainTab[]
typeStyle of the tab bar'line' | 'card' | 'button' | 'slash'
sizeSize'small' | 'medium' | 'large'
tabPositionPosition'top' | 'left'
collapsibleWhether collapsibleboolean | 'auto'
showRestInDropdownIn collapsible mode, whether collapsed tabs are listed in a dropdownboolean
moreConfiguration of the More menunumber | TabsMore
arrowPositionPosition of the arrows in collapsible mode'both' | 'start' | 'end'
visibleTabsStyleStyle of the whole scrolling area in collapsible modeStyleValue
dropdownPropsDropdown props of the arrow menus in collapsible modeTabsDropdownProps
classtabBarClassNamestring
styletabBarStyleStyleValue

TabPane

Props

PropertyDescriptionTypeDefault
itemKeyUnique key of the tab, matched against activeKey.stringundefined
disabledWhether the tab is disabled.booleanundefined
closableWhether the tab can be closed; closing emits tabClose on the Tabs.booleanundefined

Events

EventDescriptionCallback parameters
None

Slots

SlotDescriptionScope parameters
defaultPanel content.any
tabThe tab content in the bar, rendered by the Tabs. Only plain text appears as the tab field of the tabBarProps.list entries given to the tabBar slot.any
iconThe icon of the tab in the bar, rendered by the Tabs.any

Exposes

NameDescriptionType
None

class, style and native attributes (including id, role, aria-* and tabindex) land on the root element of the panel. The id, role="tabpanel", aria-hidden and the aria-labelledby that pairs it with its tab are generated by the component and are not overridden; tabindex defaults to 0 and can be overridden.

TabItem

A single tab inside a custom tab bar (the #tabBar slot). Inside a Tabs, clicking it selects its tab by itself and triggers the change and tabClick events of the Tabs.

Props

PropertyDescriptionTypeDefault
itemKeyUnique key of the tab.string""
selectedWhether the tab is selected.booleanfalse
disabledWhether the tab is disabled; clicks, the close button and the Enter, Space, Delete and Backspace keys have no effect, while the close button still shows.booleanfalse
closableWhether to show the close button.booleanfalse
sizeSize; defaults to the size of the enclosing Tabs.TabSizeundefined
typeStyle; defaults to the type of the enclosing Tabs, else line.TabTypeundefined
tabPositionPosition; defaults to the tabPosition of the enclosing Tabs, else top.TabPositionundefined

Events

EventDescriptionCallback parameters
clickEmitted when the tab is clicked, with the itemKey and the event; not emitted while disabled. Inside a Tabs the click already selects the tab.[itemKey: string, event: MouseEvent]

Slots

SlotDescriptionScope parameters
tabTab content.any
iconTab icon; an empty result renders no icon.any

Exposes

NameDescriptionType
None

class, style and native attributes land on the root element; role, id, aria-selected, aria-disabled, aria-controls and tabindex are managed by the component and are not overridden.

Accessibility

ARIA

  • About role
    • The element in TabBar that holds only the Tabs has a role of tablist; the scroll arrows, the "more" trigger and tabBarExtraContent sit outside it
    • Tab in TabBar has a role of tab
    • TabPane has a role of tabpanel
  • aria-label, aria-labelledby: When passed to Tabs they land on the role="tablist" element and name the tab bar
  • aria-orientation: Indicates TabBar's orientation, can be vertical or horizontal. When tabPosition is left,aria-orientation will be vertical, when tabPosition is top, aria-orientation will be horizontal.
  • aria-disabled: When TabPane is disabled, the related Tab's aria-disabled will be set to true.
  • aria-selected: Indicates whether the Tab is selected.
  • aria-controls: Indicates the TabPane controlled by the Tab; when only the active tab's panel is in the document (with tabList, or with keepDOM set to false), only the selected Tab carries it
  • aria-labelledby: Indicates the element labels the TabPane

Keyboard and Focus

WAI-ARIA: https://www.w3.org/WAI/ARIA/apg/patterns/tabpanel/

  • Tabs can be given focus, except for disabled tabs
  • Keyboard users can use the Tab key to move the focus to the tab panel of the selected tab element
  • Use left and right arrows to toggle options when focus is on a tab element in a horizontal tab list (the two arrows swap in an RTL page)
  • Use up and down arrows to toggle options when focus is on a tab element in a vertical tab list
  • When the focus is on an inactive tab element in the tab list, the Space or Enter keys can be used to activate the tab
  • When keyboard users want to focus directly on the last tab element in the tab list:
    • Mac users: fn + right arrow
    • Windows users: End
  • When keyboard users want to focus directly on the first tab element in the tab list:
    • Mac users: fn + left arrow
    • Windows users: Home
  • With more, the default "More" trigger is a native button: focus it with Tab, open the dropdown with Enter or Space; it carries aria-haspopup="menu" and aria-expanded
  • When a tab is allowed to be deleted:
    • Users can use the Delete or Backspace key to delete a tab, except a disabled one
    • After deletion, the focus is transferred to the next element of the deleted tab element; if the deleted element has no subsequent element, it is transferred to the previous element

Design Token

These are the component's internal Sass variables and cannot be overridden. To customize styles, override the --semi-* CSS variables (see the Design Token page) or write unlayered CSS rules.
Sass variableValueUsage
$transition_duration-tabs_tab_line-bordervar(--semi-transition_duration-none)线条式标签页标示线-边框-动画持续时间
$transition_function-tabs_tab_line-bordervar(--semi-transition_function-easeIn)线条式标签页标示线-边框-过渡曲线
$transition_delay-tabs_tab_line-bordervar(--semi-transition_delay-none)线条式标签页标示线-边框-延迟时间
$transition_duration-tabs_tab_line-textvar(--semi-transition_duration-none)线条式标签页-文字-动画持续时间
$transition_function-tabs_tab_line-textvar(--semi-transition_function-easeIn)线条式标签页-文字-过渡曲线
$transition_delay-tabs_tab_line-textvar(--semi-transition_delay-none)线条式标签页-文字-延迟时间
$transition_duration-tabs_tab_button-bgvar(--semi-transition_duration-none)按钮式标签页-背景色-动画持续时间
$transition_function-tabs_tab_button-bgvar(--semi-transition_function-easeIn)按钮式标签页-背景色-过渡曲线
$transition_delay-tabs_tab_button-bgvar(--semi-transition_delay-none)按钮式标签页-背景色-延迟时间
$transition_duration-tabs_tab_card-bgvar(--semi-transition_duration-none)卡片式标签页文字-背景色-动画持续时间
$transition_function-tabs_tab_card-bgvar(--semi-transition_function-easeIn)卡片式标签页文字-背景色-过渡曲线
$transition_delay-tabs_tab_card-bgvar(--semi-transition_delay-none)卡片式标签页文字-背景色-延迟时间
$transform_scale-tabs_tab_line-itemvar(--semi-transform_scale-none)线条式标签页item 放大
$transform_scale-tabs_tab_button-itemvar(--semi-transform_scale-none)按钮式标签页item 放大
$transform_scale-tabs_tab_card-itemvar(--semi-transform_scale-none)线条式标签页item 放大
$animation_transform_translateX-tabs_tabPanel-leftShow60px左侧展示时,tabPanel的水平偏移值
$animation_transform_translateX-tabs_tabPanel-rightShow-60px右侧展示时,tabPanel的水平偏移值
$animation_opacity-tabs_tabPanel_show0tabPanel的动画开始时透明度
$animation_duration-tabs_tabPanel-show200mstabPanel的展示动画持续时间
$animation_function-tabs_tabPanel-showease-in-outtabPanel的展示动画曲线
$animation_delay-tabs_tabPanel-show0stabPanel的展示动画延迟时间
$color-tabs_tab_line_default-border-defaultvar(--semi-color-border)线条式页签轨道颜色 - 默认
$color-tabs_tab_line_default-text-defaultvar(--semi-color-text-2)线条式页签文本颜色 - 默认
$color-tabs_tab_line_default-text-hovervar(--semi-color-text-0)线条式页签文本颜色 - 悬浮
$color-tabs_tab_line_default-border-hovervar(--semi-color-fill-0)线条式页签标示线颜色 - 悬浮
$color-tabs_tab_line_default-text-activevar(--semi-color-text-0)线条式页签文本颜色 - 按下
$color-tabs_tab_line_default-border-activevar(--semi-color-fill-1)线条式页签标示线颜色 - 按下
$color-tabs_tab_line_selected-text-defaultvar(--semi-color-text-0)线条式页签文本颜色 - 选中
$color-tabs_tab_line_indicator_selected-icon-defaultvar(--semi-color-primary)线条式页签标示线颜色 - 选中
$color-tabs_tab_line_vertical_selected-bg-defaultvar(--semi-color-primary-light-default)垂直线条式页签背景颜色 - 选中
$color-tabs_tab_line_vertical-bg-hovervar(--semi-color-fill-0)垂直线条式页签背景颜色 - 悬浮
$color-tabs_tab_line_vertical-bg-activevar(--semi-color-fill-1)垂直线条式页签背景颜色 - 按下
$color-tabs_tab_line_disabled-text-defaultvar(--semi-color-disabled-text)禁用线条式页签文本颜色 - 默认
$color-tabs_tab_line_disabled-text-hovervar(--semi-color-disabled-text)禁用线条式页签文本颜色 - 悬浮
$color-tabs_tab_card_default-border-defaultvar(--semi-color-border)卡片式页签容器底部长线颜色 - 默认
$color-tabs_tab_button_selected-bg-defaultvar(--semi-color-primary-light-default)按钮式页签背景颜色 - 选中
$color-tabs_tab_button_selected-text-defaultvar(--semi-color-primary)按钮式页签文本颜色 - 选中
$color-tabs_tab_button-text-defaultvar(--semi-color-text-2)按钮式页签文本颜色 - 默认
$color-tabs_tab_button-bg-hovervar(--semi-color-fill-0)按钮式页签背景颜色 - 悬浮
$color-tabs_tab_button-bg-activevar(--semi-color-fill-1)按钮式页签背景颜色 - 按下
$color-tabs_tab_card_indicator_selected-icon-defaultvar(--semi-color-border)卡片式页签选中页签描边
$color-tabs_tab_card-bg-hovervar(--semi-color-fill-0)卡片式页签背景颜色 - 悬浮
$color-tabs_tab_card_selected-bg-defaultvar(--semi-color-bg-1)卡片式页签背景颜色 - 选中
$color-tabs_tab_card-bg-activevar(--semi-color-fill-1)卡片式页签背景颜色 -按下
$color-tabs_tab-icon-defaultvar(--semi-color-text-2)页签图标颜色 - 默认
$color-tabs_tab-icon-hovervar(--semi-color-text-0)页签图标颜色 - 悬浮
$color-tabs_tab-icon-activevar(--semi-color-text-0)页签图标颜色 - 按下
$color-tabs_tab_selected-icon-defaultvar(--semi-color-primary)页签图标颜色 - 选中
$color-tabs_tab-outline-focus$color-focus-ring页签轮廓 - 聚焦
$color-tabs_tab-pane-text-defaultvar(--semi-color-text-0)标签页内容文本颜色 - 默认
$color-tabs_tab-pane_arrow-text-defaultvar(--semi-color-primary)滚动折叠箭头颜色 - 默认
$color-tabs_tab-pane_arrow-border-defaulttransparent滚动折叠箭头边框颜色 - 默认
$color-tabs_tab-pane_arrow-bg-defaulttransparent滚动折叠箭头背景色 - 默认
$color-tabs_tab-pane_arrow-text-hovervar(--semi-color-primary)滚动折叠箭头颜色 - 悬浮
$color-tabs_tab-pane_arrow-border-hovertransparent滚动折叠箭头边框颜色 - 悬浮
$color-tabs_tab-pane_arrow-text-activevar(--semi-color-primary)滚动折叠箭头颜色 - 按下
$color-tabs_tab-pane_arrow-border-activetransparent滚动折叠箭头边框颜色 - 按下
$color-tabs_tab-pane_arrow_disabled-bg-defaulttransparent
$color-tabs_tab-pane_arrow_disabled-bg-hovertransparent
$color-tabs_tab-pane_arrow_disabled-text-defaultvar(--semi-color-disabled-text)
$color-tabs_tab-pane_arrow_disabled-text-hovervar(--semi-color-disabled-text)
$color-tabs_tab_slash_linevar(--semi-color-text-2)斜线式页签分割线颜色
$font-tabs_tab-fontWeight$font-weight-regular页签文本字重 - 默认
$font-tabs_tab_active-fontWeight$font-weight-bold页签文本字重 - 选中
$height-tabs_overflow_list300px页签折叠收起菜单高度
$width-tabs_bar_line-border$border-thickness-control线条式页签底部分割线宽度
$width-tabs_bar_line_tab-border2px页签标示线宽度
$width-tabs_bar_card-border$border-thickness-control卡片式页签容器底部长线宽度
$width-tabs-outline$width-focus-ring聚焦轮廓宽度
$width-tabs-outline-offset-2px聚焦轮廓偏移宽度
$width-tabs_bar_line-outline-offset-1px线条式页签聚焦轮廓偏移宽度
$width-tabs_tab-pane_arrow-border0px滚动折叠箭头边框宽度
$width-tabs_tab_slash_line8px斜线式页签分割线宽度
$height-tabs_tab_slash_line14px斜线式页签分割线高度
$height-tabs_bar_extra_large50px大尺寸页签高度
$font-tabs_bar_extra_large-lineHeight$height-tabs_bar_extra_large大尺寸页签文字行高
$height-tabs_bar_extra_small36px小尺寸页签高度
$font-tabs_bar_extra_small-lineHeight$height-tabs_bar_extra_small小尺寸页签文字行高
$spacing-tabs_tab-more_trigger_icon-marginLeft8px
$spacing-tabs_tab-more_trigger_icon-marginRight8px
$spacing-tabs_tab-more_trigger_icon-marginTop0px
$spacing-tabs_tab-more_trigger_icon-marginBottom0px
$spacing-tabs_tab-pane_arrow8px滚动折叠箭头内边距
$spacing-tabs_bar_extra-paddingY0px附加操作垂直内边距
$spacing-tabs_bar_extra-paddingX5px附加操作水平内边距
$spacing-tabs_tab_icon-marginRight$spacing-tight附加操作垂直内边距
$spacing-tabs_tab_icon-top3px页签图标顶部位置
$spacing-tabs_overflow_icon-marginRight4px页签折叠切换按钮右侧外边距
$spacing-tabs_overflow_icon-marginLeft4px页签折叠切换按钮左侧外边距
$spacing-tabs_bar_line_tab-paddingTop$spacing-base线条式页签
$spacing-tabs_bar_line_tab-paddingRight$spacing-extra-tight线条式页签右侧内边距
$spacing-tabs_bar_line_tab-paddingBottom$spacing-base - $width-tabs_bar_line_tab-border线条式页签底部内边距
$spacing-tabs_bar_line_tab-paddingLeft$spacing-extra-tight线条式页签左侧内边距
$spacing-tabs_bar_line_tab-marginRight$spacing-loose线条式页签右侧外边距
$spacing-tabs_bar_line_tab_small-paddingTop$spacing-tight小尺寸线条式页签顶部内边距
$spacing-tabs_bar_line_tab_small-paddingRight$spacing-extra-tight小尺寸线条式页签右侧内边距
$spacing-tabs_bar_line_tab_small-paddingBottom$spacing-tight - $width-tabs_bar_line_tab-border小尺寸线条式页签底部内边距
$spacing-tabs_bar_line_tab_small-paddingLeft$spacing-extra-tight小尺寸线条式页签左侧内边距
$spacing-tabs_bar_line_tab_medium-paddingTop$spacing-base-tight中等尺寸线条式页签顶部内边距
$spacing-tabs_bar_line_tab_medium-paddingRight$spacing-extra-tight中等尺寸线条式页签右侧内边距
$spacing-tabs_bar_line_tab_medium-paddingBottom$spacing-base-tight - $width-tabs_bar_line_tab-border中等尺寸线条式页签底部内边距
$spacing-tabs_bar_line_tab_medium-paddingLeft$spacing-extra-tight中等尺寸线条式页签左侧内边距
$spacing-tabs_bar_line_tab_left-padding12px垂直线条式页签左侧内边距
$spacing-tabs_bar_line_tab_left_small-padding$spacing-tight - 2px小尺寸垂直线条式页签左侧内边距
$spacing-tabs_bar_line_tab_left_medium-padding$spacing-base-tight - 2px中等尺寸垂直线条式页签左侧内边距
$spacing-tabs_bar_slash_tab-paddingY12px斜线式页签上下内边距
$spacing-tabs_bar_slash_tab-paddingX0px斜线式页签水平内边距
$spacing-tabs_bar_slash-marginRight16px斜线式页签右侧外边距
$spacing-tabs_bar_slash_line_marginLeft16px斜线式页签斜线左侧外边距
$spacing-tabs_bar_slash_line_marginTop3px斜线式页签斜线顶部外边距
$spacing-tabs_bar_slash_line_marginBottom3px斜线式页签斜线底部外边距
$spacing-tabs_content-paddingY5px页签内容区垂直方向内边距
$spacing-tabs_content-paddingX0页签内容区水平方向内边距
$spacing-tabs_content_left-paddingX5px垂直页签内容区垂直方向内边距
$spacing-tabs_content_left-paddingY0垂直页签内容区水平方向内边距
$spacing-tabs_bar_card_tab-marginRight$spacing-tight卡片式页签右侧外边距
$spacing-tabs_bar_card_tab_active-paddingTop$spacing-tight卡片式选中页签顶部内边距
$spacing-tabs_bar_card_tab_active-paddingBottom$spacing-tight - 1px卡片式选中页签底部内边距
$spacing-tabs_bar_card_tab_active-paddingLeft$spacing-base-tight卡片式选中页签左侧内边距
$spacing-tabs_bar_card_tab_active-paddingRight$spacing-base-tight卡片式选中页签右侧内边距
$spacing-tabs_bar_card_tab_left-marginBottom$spacing-tight垂直卡片式页签底部外边距
$spacing-tabs_bar_card_tab_left_active-paddingY$spacing-tight垂直卡片式选中页签垂直内边距
$spacing-tabs_bar_card_tab_left_active-paddingX$spacing-base-tight垂直卡片式选中页签水平内边距
$spacing-tabs_bar_card_tab-paddingY$spacing-tight卡片式选中页签垂直内边距
$spacing-tabs_bar_card_tab-paddingX$spacing-base-tight卡片式选中页签水平内边距
$spacing-tabs_bar_button_tab_left-marginBottom$spacing-tight垂直按钮式页签底部外边距
$spacing-tabs_bar_button_tab-marginRight$spacing-tight按钮式页签右侧外边距
$spacing-tabs_bar_button_tab-paddingY$spacing-tight按钮式页签垂直内边距
$spacing-tabs_bar_button_tab-paddingX$spacing-base-tight按钮式页签水平内边距
$radius-tabs_tab_cardvar(--semi-border-radius-small) var(--semi-border-radius-small) 0 0卡片式页签四向圆角
$radius-tabs_tab_card_leftvar(--semi-border-radius-small) 0 0 var(--semi-border-radius-small)垂直卡片式页签四向圆角
$radius-tabs_tab_buttonvar(--semi-border-radius-small)按钮式页签圆角
$font-tabs_bar_large-fontSize$font-size-regular大号模式 字体大小
$font-tabs_bar_small-fontSize$font-size-regular小号模式 字体大小
$font-tabs_bar_medium-fontSize$font-size-regular中等模式 字体大小

Content Guidelines

  • Label copy needs to explain the label content accurately and clearly
  • Use short, easily distinguishable labels
  • try to stay within one word

FAQ

  • Why typography with ellipses in Tabs doesn't work?

    Because when Tabs renders TabPane, the default is to render display: none. At this point these components cannot get the correct width or height values. It is recommended to enable lazyRender in or disable keepDOM.

  • Why are the height or width values ​​wrong when using components such as Collapse/Collapsible/Resizable Table in Tabs?

    The reason is the same as above. In addition, if the collapse does not need animation, you can also turn off the animation effect by setting its motion to false. There is no need to get the height of the component at this point。