refactor: 前端 UI 框架从 TDesign 迁移到 antd 6.x
- 移除 tdesign-react + tdesign-icons-react,新增 antd@6.4.3 + @ant-design/icons@6.2.3 - Layout/Header/Sider/Content 替换 TDesign Layout,Sider 内置折叠管理 - Segmented 替换 RadioGroup 主题切换,ConfigProvider 主题算法切换 - Menu items prop 模式,Sidebar 简化为无 props 纯组件 - Table/Modal/Form/Input.TextArea/Tabs/Tag/Popconfirm 全量迁移 - App.useApp().message 替换 MessagePlugin(hooks 模式) - --td-* CSS 变量替换为 --ant-* antd CSS 变量 - 测试适配:ConfigProvider+App wrapper,.ant-menu-item-selected,antd CSS-in-JS jsdom 兼容 - 文档更新:frontend.md, development/README.md, config.yaml, deploy.md - vendor-antd chunk 755KB gzipped 240KB
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
import type { ErrorInfo, ReactNode } from "react";
|
||||
|
||||
import { Alert, Button, Space } from "antd";
|
||||
import { Component } from "react";
|
||||
import { Alert, Button, Space } from "tdesign-react";
|
||||
|
||||
interface Props {
|
||||
children: ReactNode;
|
||||
@@ -25,9 +25,9 @@ export class ErrorBoundary extends Component<Props, State> {
|
||||
override render() {
|
||||
if (this.state.hasError) {
|
||||
return (
|
||||
<Space align="center" className="error-boundary-fallback" direction="vertical" size="large">
|
||||
<Alert message="页面渲染出现异常,请刷新重试" theme="error" title="页面出错" />
|
||||
<Button onClick={() => window.location.reload()} theme="primary">
|
||||
<Space align="center" className="error-boundary-fallback" size="large" vertical>
|
||||
<Alert showIcon title="页面渲染出现异常,请刷新重试" type="error" />
|
||||
<Button onClick={() => window.location.reload()} type="primary">
|
||||
刷新页面
|
||||
</Button>
|
||||
</Space>
|
||||
|
||||
@@ -1,26 +1,28 @@
|
||||
import type { MenuProps } from "antd";
|
||||
|
||||
import { Menu } from "antd";
|
||||
import { useLocation, useNavigate } from "react-router";
|
||||
import { ChevronLeftIcon, ChevronRightIcon } from "tdesign-icons-react";
|
||||
import { Button, Menu } from "tdesign-react";
|
||||
|
||||
import { MENU_ITEMS } from "../../menu";
|
||||
|
||||
const { MenuItem } = Menu;
|
||||
type MenuItem = Required<MenuProps>["items"][number];
|
||||
|
||||
interface SidebarProps {
|
||||
collapsed: boolean;
|
||||
onToggleCollapsed: () => void;
|
||||
}
|
||||
|
||||
export function Sidebar({ collapsed, onToggleCollapsed }: SidebarProps) {
|
||||
export function Sidebar() {
|
||||
const navigate = useNavigate();
|
||||
const location = useLocation();
|
||||
|
||||
const currentPath = location.pathname;
|
||||
const currentItem = MENU_ITEMS.find((item) => item.path === currentPath);
|
||||
const activeValue = currentItem?.value ?? "";
|
||||
const selectedKeys = currentItem ? [currentItem.value] : [];
|
||||
|
||||
const handleMenuChange = (value: number | string) => {
|
||||
const item = MENU_ITEMS.find((item) => item.value === value);
|
||||
const menuItems: MenuItem[] = MENU_ITEMS.map((item) => ({
|
||||
icon: item.icon,
|
||||
key: item.value,
|
||||
label: item.label,
|
||||
}));
|
||||
|
||||
const handleMenuClick: MenuProps["onClick"] = ({ key }) => {
|
||||
const item = MENU_ITEMS.find((i) => i.value === key);
|
||||
if (item) {
|
||||
void navigate(item.path);
|
||||
}
|
||||
@@ -29,25 +31,10 @@ export function Sidebar({ collapsed, onToggleCollapsed }: SidebarProps) {
|
||||
return (
|
||||
<Menu
|
||||
className="app-sidebar-menu"
|
||||
collapsed={collapsed}
|
||||
onChange={handleMenuChange}
|
||||
operations={
|
||||
<Button
|
||||
className="app-sidebar-collapse-btn"
|
||||
icon={collapsed ? <ChevronRightIcon /> : <ChevronLeftIcon />}
|
||||
onClick={onToggleCollapsed}
|
||||
shape="square"
|
||||
variant="text"
|
||||
/>
|
||||
}
|
||||
value={activeValue}
|
||||
width={collapsed ? "64px" : "232px"}
|
||||
>
|
||||
{MENU_ITEMS.map((item) => (
|
||||
<MenuItem icon={item.icon} key={item.value} value={item.value}>
|
||||
{item.label}
|
||||
</MenuItem>
|
||||
))}
|
||||
</Menu>
|
||||
items={menuItems}
|
||||
mode="inline"
|
||||
onClick={handleMenuClick}
|
||||
selectedKeys={selectedKeys}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user