Files
lab/ts/web/nextjs/polaris/src/features/navigation/components/sidebar.tsx
T
2026-09-02 23:53:28 +08:00

106 lines
3.1 KiB
TypeScript

import { Home, PanelLeftClose, PanelLeftOpen } from "lucide-react"
import Image from "next/image"
import Link from "next/link"
import { Button } from "@/components/ui/button"
import {
Tooltip,
TooltipContent,
TooltipProvider,
TooltipTrigger,
} from "@/components/ui/tooltip"
import { CategoryIcon } from "@/features/navigation/components/category-icon"
import { cn } from "@/lib/utils"
import type { Category } from "@/types/navigation"
type SidebarProps = {
categories: Category[]
siteName: string
collapsed: boolean
onToggle: () => void
}
export function Sidebar({
categories,
siteName,
collapsed,
onToggle,
}: SidebarProps) {
const ToggleIcon = collapsed ? PanelLeftOpen : PanelLeftClose
const toggleLabel = collapsed ? "展开侧边栏" : "折叠侧边栏"
return (
<TooltipProvider>
<aside className="sidebar" aria-label="主导航">
<div className="sidebar__header">
<Link
className="sidebar__brand"
href="/"
aria-label={`${siteName} 首页`}
>
<Image
src="/brand/logo.svg"
alt=""
width={40}
height={40}
priority
/>
<span className={cn("sidebar__site-name", collapsed && "sr-only")}>
{siteName}
</span>
</Link>
<Button
type="button"
variant="ghost"
size="icon"
aria-label={toggleLabel}
onClick={onToggle}
>
<ToggleIcon aria-hidden="true" />
</Button>
</div>
<nav className="sidebar__nav" aria-label="站点导航">
<Link
className="sidebar__nav-item sidebar__nav-item--active"
href="/"
aria-current="page"
>
<Home aria-hidden="true" />
<span className={cn("sidebar__label", collapsed && "sr-only")}>
首页
</span>
</Link>
<div className="sidebar__categories">
{/* 本次只验收首页;分类页完成前保持可见但禁用,避免用户进入 404。 */}
{categories.map((category) => (
<Tooltip key={category.id}>
<TooltipTrigger asChild>
<Button
type="button"
variant="ghost"
className="sidebar__nav-item"
aria-disabled="true"
aria-label={`${category.title},分类页将在下一阶段提供`}
>
<CategoryIcon name={category.icon} />
<span
className={cn("sidebar__label", collapsed && "sr-only")}
>
{category.title}
</span>
</Button>
</TooltipTrigger>
<TooltipContent side="right">
分类页将在下一阶段提供
</TooltipContent>
</Tooltip>
))}
</div>
</nav>
</aside>
</TooltipProvider>
)
}