your-workflow/frontend/src/pages/Layout.jsx

110 lines
3.6 KiB
JavaScript

import React, { useState } from "react";
import { Outlet, useNavigate, useLocation } from "react-router-dom";
import { Layout, Menu, Button, Flex, Dropdown, Steps } from "antd";
import { MenuFoldOutlined, MenuUnfoldOutlined, UserOutlined, LoginOutlined, ProfileOutlined, NodeExpandOutlined, LaptopOutlined } from "@ant-design/icons";
import { useAuth } from "../context/AuthContext";
import './Layout.css';
const { Header, Sider, Content } = Layout;
export default function LayoutPage() {
const { logout, user } = useAuth();
const [collapsed, setCollapsed] = useState(true);
const navigate = useNavigate();
const location = useLocation();
const menuItems = [
{ key: "1", icon: <NodeExpandOutlined />, label: "工作台", path: "/flow" },
{ key: "2", icon: <LaptopOutlined />, label: "节点管理", path: "/client" },
];
const selectedKey = menuItems.find(item => location.pathname.startsWith(item.path))?.key || "";
return (
<Layout className="page-layout">
<Sider trigger={null} collapsible collapsed={collapsed} width={200}>
<Logo collapsed={collapsed} />
<Menu
theme="dark"
mode="inline"
selectedKeys={[selectedKey]}
items={menuItems}
onClick={({ key }) => {
const item = menuItems.find(i => i.key === key);
if (item) navigate(item.path);
}}
/>
</Sider>
<Layout className="page-content">
<Header style={{ padding: 0, backgroundColor: 'white', width: "100%" }}>
<Flex align="center" justify="space-between" style={{
height: '100%',
padding: '0 8px',
boxSizing: 'border-box'
}}>
<Button
style={{ border: 'none'}}
type='text'
icon={collapsed ? <MenuUnfoldOutlined /> : <MenuFoldOutlined />}
onClick={() => setCollapsed(!collapsed)}
/>
<HeaderRight logout={logout} navigate={navigate} user={user} />
</Flex>
</Header>
<Content
style={{
margin: "24px 16px",
minHeight: 280,
}}
>
<Outlet /> {/* 渲染子路由 */}
</Content>
</Layout>
</Layout>
);
}
const Logo = ({ collapsed }) => {
return <div className="logo">
{collapsed ? "F" : "FLOW"}
</div>
}
const HeaderRight = ({ logout, navigate, user }) => {
const items = [
{
label: '用户信息',
key: '2',
icon: <ProfileOutlined />
},
{
type: 'divider',
},
{
label: '退出登录',
key: '1',
icon: <LoginOutlined/>
},
];
const onClick = ({ key }) => {
if (key === '1') {
logout();
}
if (key === '2') {
navigate('/user/detail')
}
}
return (
<Dropdown menu={{ items, onClick }} arrow>
<a onClick={e => e.preventDefault()}>
<Button type="text"
style={{ border: 'none' }}
icon={<UserOutlined />}
>
{user?.username}
</Button>
</a>
</Dropdown>
)
}