Tabs 标签页
分隔内容上有关联但属于不同类别的数据集合。
基础用法
基础的、简洁的标签页。
vue
<template>
<NTabs v-model="activeTab">
<NTabPane name="tab1" label="标签一">
<p>内容一</p>
</NTabPane>
<NTabPane name="tab2" label="标签二">
<p>内容二</p>
</NTabPane>
<NTabPane name="tab3" label="标签三">
<p>内容三</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
const activeTab = ref('tab1')
</script>卡片风格
设置 type="card" 来启用卡片风格。
vue
<template>
<NTabs v-model="activeTab" type="card">
<NTabPane name="tab1" label="标签一">
<p>内容一</p>
</NTabPane>
<NTabPane name="tab2" label="标签二">
<p>内容二</p>
</NTabPane>
<NTabPane name="tab3" label="标签三">
<p>内容三</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
const activeTab = ref('tab1')
</script>带边框的卡片
设置 type="border-card" 来启用带边框的卡片风格。
vue
<template>
<NTabs v-model="activeTab" type="border-card">
<NTabPane name="tab1" label="标签一">
<p>内容一</p>
</NTabPane>
<NTabPane name="tab2" label="标签二">
<p>内容二</p>
</NTabPane>
<NTabPane name="tab3" label="标签三">
<p>内容三</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
const activeTab = ref('tab1')
</script>可关闭
设置 closable 属性来启用关闭功能。
vue
<template>
<NTabs v-model="activeTab" type="card" closable @tab-remove="handleRemove">
<NTabPane
v-for="tab in tabs"
:key="tab.name"
:name="tab.name"
:label="tab.label"
>
<p>{{ tab.content }}</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
const activeTab = ref('tab1')
const tabs = ref([
{ name: 'tab1', label: '标签一', content: '内容一' },
{ name: 'tab2', label: '标签二', content: '内容二' },
{ name: 'tab3', label: '标签三', content: '内容三' },
])
const handleRemove = (name) => {
const index = tabs.value.findIndex(tab => tab.name === name)
if (index !== -1) {
tabs.value.splice(index, 1)
if (activeTab.value === name) {
activeTab.value = tabs.value[0]?.name || ''
}
}
}
</script>标签位置
使用 tab-position 属性来设置标签的位置。
vue
<template>
<div style="margin-bottom: 20px;">
<NRadioGroup v-model="position">
<NRadio value="top">顶部</NRadio>
<NRadio value="right">右侧</NRadio>
<NRadio value="bottom">底部</NRadio>
<NRadio value="left">左侧</NRadio>
</NRadioGroup>
</div>
<NTabs v-model="activeTab" :tabPosition="position">
<NTabPane name="tab1" label="标签一">
<p>内容一</p>
</NTabPane>
<NTabPane name="tab2" label="标签二">
<p>内容二</p>
</NTabPane>
<NTabPane name="tab3" label="标签三">
<p>内容三</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
const activeTab = ref('tab1')
const position = ref('top')
</script>禁用标签
在 NTabPane 中设置 disabled 属性来禁用标签。
vue
<template>
<NTabs v-model="activeTab">
<NTabPane name="tab1" label="标签一">
<p>内容一</p>
</NTabPane>
<NTabPane name="tab2" label="标签二" disabled>
<p>内容二</p>
</NTabPane>
<NTabPane name="tab3" label="标签三">
<p>内容三</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
const activeTab = ref('tab1')
</script>自定义标签
使用 label 插槽来自定义标签内容。
vue
<template>
<NTabs v-model="activeTab">
<NTabPane name="tab1">
<template #label>
<span>🔔 标签一</span>
</template>
<p>内容一</p>
</NTabPane>
<NTabPane name="tab2">
<template #label>
<span>📧 标签二</span>
</template>
<p>内容二</p>
</NTabPane>
<NTabPane name="tab3">
<template #label>
<span>⚙️ 标签三</span>
</template>
<p>内容三</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
const activeTab = ref('tab1')
</script>动态增减标签
结合卡片标签和可关闭功能,实现动态增减标签。
vue
<template>
<div style="margin-bottom: 20px;">
<NButton size="small" @click="addTab">添加标签</NButton>
</div>
<NTabs v-model="activeTab" type="card" closable @tab-remove="removeTab">
<NTabPane
v-for="tab in tabs"
:key="tab.name"
:name="tab.name"
:label="tab.label"
>
<p>{{ tab.content }}</p>
</NTabPane>
</NTabs>
</template>
<script setup>
import { ref } from 'vue'
let tabIndex = 3
const activeTab = ref('tab1')
const tabs = ref([
{ name: 'tab1', label: '标签一', content: '内容一' },
{ name: 'tab2', label: '标签二', content: '内容二' },
{ name: 'tab3', label: '标签三', content: '内容三' },
])
const addTab = () => {
tabIndex++
const newTab = {
name: `tab${tabIndex}`,
label: `标签${tabIndex}`,
content: `内容${tabIndex}`,
}
tabs.value.push(newTab)
activeTab.value = newTab.name
}
const removeTab = (name) => {
const index = tabs.value.findIndex(tab => tab.name === name)
if (index !== -1) {
tabs.value.splice(index, 1)
if (activeTab.value === name) {
activeTab.value = tabs.value[0]?.name || ''
}
}
}
</script>Tabs API
Props
| 属性 | 说明 | 类型 | 默认值 |
|---|---|---|---|
| modelValue | 绑定值,选中选项卡的 name | string | number | — |
| type | 风格类型 | '' | 'card' | 'border-card' | '' |
| closable | 标签是否可关闭 | boolean | false |
| tabPosition | 选项卡所在位置 | 'top' | 'right' | 'bottom' | 'left' | 'top' |
Events
| 事件名 | 说明 | 类型 |
|---|---|---|
| update:modelValue | 绑定值变化时触发 | (name: string | number) => void |
| tab-click | tab 被选中时触发 | (pane: any) => void |
| tab-remove | 点击 tab 移除按钮时触发 | (name: string | number) => void |
| tab-add | 点击 tab 新增按钮时触发 | () => void |
| edit | 点击 tab 的新增或移除按钮后触发 | (targetName: string | number | undefined, action: 'add' | 'remove') => void |
TabPane API
Props
| 属性 | 说明 | 类型 | 默认值 |
|---|---|---|---|
| name | 选项卡的标识 | string | number | — |
| label | 选项卡的标题 | string | — |
| disabled | 是否禁用 | boolean | false |
| closable | 标签是否可关闭 | boolean | — |
Slots
| 插槽名 | 说明 |
|---|---|
| default | 选项卡的内容 |
| label | 选项卡的标题内容 |