Files
xiaoxia-saas/apps/web/src/components/layout/Sidebar.tsx
T
CI Test f0eed0ca3f
Deploy / Build Production Runtime Images (push) Has been skipped
Deploy / Deploy Production (push) Has been skipped
Deploy / Production Browser E2E (push) Has been skipped
Deploy / Deploy Staging (push) Failing after 192h26m58s
CI/CD Pipeline / Frontend Lint (push) Failing after 192h27m37s
CI/CD Pipeline / Validate Code Quality And Tests (push) Failing after 192h27m46s
style: fix prettier formatting issues
2026-07-01 12:26:48 +08:00

70 lines
2.2 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/**
* Sidebar - 侧边栏导航组件(Task 1.3
*
* 功能:
* - 分组导航菜单(创作工具 / 资源管理 / 系统)
* - 每个菜单项:图标 + 文字
* - 当前页面对应菜单项高亮(基于路由匹配)
* - 点击跳转路由
* - 折叠态:仅显示图标,隐藏文字(通过 SidebarContext 读取 collapsed 状态)
* - 响应式:移动端自动折叠
*/
import React, { useContext } from "react";
import { useLocation, useNavigate } from "react-router-dom";
import { SidebarContext } from "./MainLayout";
import { NAV_GROUPS } from "@/config/navigation";
import "./Sidebar.css";
/** 判断菜单项是否激活 */
const isMenuItemActive = (pathname: string, path: string): boolean => {
if (path === "/dashboard") {
return pathname === "/" || pathname === "/dashboard";
}
return pathname.startsWith(path);
};
const Sidebar: React.FC = () => {
const { collapsed } = useContext(SidebarContext);
const location = useLocation();
const navigate = useNavigate();
const handleNavigate = (path: string) => {
navigate(path);
};
return (
<div
className={`xx-sidebar-nav${collapsed ? " xx-sidebar-nav--collapsed" : ""}`}
>
{NAV_GROUPS.map((group) => (
<div className="xx-sidebar-group" key={group.title}>
{!collapsed && (
<div className="xx-sidebar-group-title">{group.title}</div>
)}
<ul className="xx-sidebar-menu" role="menu">
{group.items.map((item) => {
const active = isMenuItemActive(location.pathname, item.path);
return (
<li
key={item.key}
className={`xx-sidebar-menu-item${active ? " xx-active" : ""}`}
role="menuitem"
title={collapsed ? item.label : undefined}
onClick={() => handleNavigate(item.path)}
>
<span className="xx-sidebar-menu-icon">{item.icon}</span>
{!collapsed && (
<span className="xx-sidebar-menu-label">{item.label}</span>
)}
</li>
);
})}
</ul>
</div>
))}
</div>
);
};
export default Sidebar;