导航组件
标签页
在同一区域切换多组内容,支持键盘导航(方向键切换)和 ARIA tablist 语义。
安装
pnpm dlx shadcn@latest add tabs -c packages/react默认
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsDefault() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore">
<TabsList>
{TABS.map((tab) => (
<TabsTrigger key={tab.value} value={tab.value}>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}带图标
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsWithIcons() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList>
{TABS.map(({ icon: Icon, name, value }) => (
<TabsTrigger key={value} value={value} className="flex items-center gap-1 px-2.5 sm:px-3">
<Icon />
{name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}带徽章
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
import { Badge } from "@polyui/react/badge"
export function TabsWithBadge() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList>
{TABS.map((tab) => (
<TabsTrigger key={tab.value} value={tab.value} className="flex items-center gap-1 px-2.5 sm:px-3">
{tab.name}
<Badge className="h-5 min-w-5 px-1 tabular-nums">{tab.count}</Badge>
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}实色胶囊
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsSolidPills() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList className="bg-background">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="data-active:bg-primary dark:data-active:bg-primary data-active:text-primary-foreground dark:data-active:text-primary-foreground dark:data-active:border-transparent"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}描边胶囊
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsOutlinedPills() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList className="bg-background">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="data-active:border-border data-active:shadow-none"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}下划线
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsUnderline() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList className="bg-background rounded-none border-b p-0">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="bg-background data-active:border-primary dark:data-active:border-primary h-full rounded-none border-0 border-b-2 border-transparent data-active:shadow-none"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}直角
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsSharp() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList className="bg-background rounded-none border-b p-0">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="bg-background data-active:border-primary dark:data-active:border-primary h-full rounded-none border-b-2 border-transparent data-active:shadow-none"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}悬浮
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsLifted() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList className="bg-background justify-start rounded-none border-b p-0">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="bg-background border-b-border dark:data-active:bg-background data-active:border-border data-active:border-b-background h-full rounded-none rounded-t border border-transparent data-active:-mb-0.5 data-active:shadow-none dark:border-b-0 dark:data-active:-mb-0.5"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}自定义
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsCustom() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList className="bg-background gap-1">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="data-active:bg-primary dark:data-active:bg-primary data-active:text-primary-foreground dark:data-active:text-primary-foreground text-muted-foreground hover:text-foreground hover:bg-muted transition-colors duration-300 hover:border dark:data-active:border-transparent"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}自定义下划线
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsCustomUnderline() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" className="gap-4">
<TabsList className="bg-background rounded-none border-b p-0">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="bg-background data-active:border-primary dark:data-active:border-primary data-active:text-foreground text-muted-foreground dark:text-muted-foreground hover:text-foreground dark:hover:text-foreground hover:border-muted-foreground/30 h-full rounded-none border-0 border-b-2 border-transparent data-active:shadow-none"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}垂直
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsVertical() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" orientation="vertical">
<TabsList className="h-full">
{TABS.map((tab) => (
<TabsTrigger key={tab.value} value={tab.value} className="w-full">
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}垂直下划线
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsVerticalUnderline() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" orientation="vertical">
<TabsList className="bg-background h-full rounded-none border-l p-0">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="bg-background data-active:border-primary dark:data-active:border-primary h-full w-full justify-start rounded-none border-0 border-l-2 border-transparent data-active:shadow-none"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}垂直柔和
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsVerticalSoft() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" orientation="vertical">
<TabsList className="bg-background h-full">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="data-active:bg-primary/20 data-active:text-primary dark:data-active:text-primary dark:data-active:bg-primary/20 w-full data-active:shadow-none dark:data-active:border-transparent"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}垂直实色
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsVerticalSolid() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" orientation="vertical">
<TabsList className="bg-background h-full">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="data-active:bg-primary dark:data-active:bg-primary data-active:text-primary-foreground dark:data-active:text-primary-foreground w-full dark:data-active:border-transparent"
>
{tab.name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}垂直带图标
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
export function TabsVerticalWithIcons() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" orientation="vertical">
<TabsList className="h-full">
{TABS.map(({ icon: Icon, name, value }) => (
<TabsTrigger
key={value}
value={value}
className="flex w-full items-center justify-start gap-1.5 px-2.5 sm:px-3"
>
<Icon />
{name}
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}垂直带徽章
Discover fresh ideas, trending topics, and hidden gems curated just for you. Start exploring and let your curiosity lead the way!
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@polyui/react/tabs"
import { Badge } from "@polyui/react/badge"
export function TabsVerticalWithBadge() {
return (
<div className="w-full max-w-md">
<Tabs defaultValue="explore" orientation="vertical">
<TabsList className="h-full gap-1.5">
{TABS.map((tab) => (
<TabsTrigger
key={tab.value}
value={tab.value}
className="flex w-full items-center justify-start gap-1.5 px-2.5 sm:px-3"
>
{tab.name}
<Badge className="h-5 min-w-5 px-1 tabular-nums">{tab.count}</Badge>
</TabsTrigger>
))}
</TabsList>
{TABS.map((tab) => (
<TabsContent key={tab.value} value={tab.value}>
<p className="text-muted-foreground text-sm">{tab.content}</p>
</TabsContent>
))}
</Tabs>
</div>
)
}属性
Tabs
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
defaultValue | string | — | 非受控默认选中项 |
value | string | — | 受控选中项 |
onValueChange | (value: string) => void | — | 切换回调 |
orientation | "horizontal" | "vertical" | "horizontal" | 布局方向 |
TabsTrigger
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
value* | string | — | 对应的 content 标识 |
disabled | boolean | false | 禁用此标签 |
TabsContent
| 属性 | 类型 | 默认值 | 说明 |
|---|---|---|---|
value* | string | — | 对应的 trigger 标识 |
forceMount | boolean | false | 始终挂载 DOM(用于 SSR 或动画) |