feat(ideContainer): 新增顶部导航栏功能

- 添加顶部导航栏组件,实现菜单切换和关闭功能
- 优化页面布局,使用 flex 布局
- 调整日志栏样式,使其覆盖整个底部
master
钟良源 5 months ago
parent 0064a22712
commit 2b7b0b31fb

@ -1,11 +1,13 @@
import React, { useEffect, useState } from 'react'; import React, { useEffect, useState } from 'react';
import { ResizeBox } from '@arco-design/web-react';
import { getUrlParams } from '@/utils/common';
import styles from './style/index.module.less'; import styles from './style/index.module.less';
import SideBar from './sideBar'; import SideBar from './sideBar';
import LogBar from './logBar'; import LogBar from './logBar';
import RightSideBar from './rightSideBar'; import RightSideBar from './rightSideBar';
import { getUrlParams } from '@/utils/common'; import NavBar from './navBar';
import ProjectContainer from '@/pages/orchestration/project'; import ProjectContainer from '@/pages/orchestration/project';
import { ResizeBox } from '@arco-design/web-react'; import { menuData, menuData2 } from './config/menuData';
interface Selected { interface Selected {
currentPath?: string; currentPath?: string;
@ -40,7 +42,8 @@ function IDEContainer() {
// 根据选中的菜单项渲染对应组件 // 根据选中的菜单项渲染对应组件
const renderContent = () => { const renderContent = () => {
switch (selected.currentPath) { const path = selected.currentPath;
switch (path) {
case 'appFlow': case 'appFlow':
return <ProjectContainer />; return <ProjectContainer />;
case 'compList': case 'compList':
@ -73,6 +76,59 @@ function IDEContainer() {
setSubMenuWidth(width); setSubMenuWidth(width);
}; };
// 根据identity获取对应的菜单数据
const getCurrentMenuData = () => {
switch (urlParams.identity) {
case 'scene':
return menuData;
case 'componentDevelopment':
return menuData2;
default:
return menuData;
}
};
// 处理tab切换
const handleTabChange = (path: string) => {
if (path) {
// 根据path查找对应的菜单项
const findMenuItem = (menuItems: any[], path: string): any => {
for (const item of menuItems) {
if (item.path === path) {
return item;
}
if (item.children) {
const found = findMenuItem(item.children, path);
if (found) return found;
}
}
return null;
};
const menuItems = getCurrentMenuData();
const menuItem = findMenuItem(menuItems, path);
if (menuItem) {
setSelected({
currentPath: menuItem.path,
currentKey: '' // 这里可以优化为实际的key值
});
}
}
else {
// 没有激活的tab重置selected状态
setSelected({});
}
};
// 处理tab关闭
const handleTabClose = (path: string) => {
// 如果关闭的是当前激活的tab则重置selected状态
if (path === selected.currentPath) {
setSelected({});
}
};
return ( return (
<> <>
<div className={styles.IDEContainer}> <div className={styles.IDEContainer}>
@ -102,7 +158,16 @@ function IDEContainer() {
</ResizeBox> </ResizeBox>
<div className={styles.mainContent}> <div className={styles.mainContent}>
{/*顶部导航栏*/}
<NavBar
selected={selected}
menuData={getCurrentMenuData()}
onTabChange={handleTabChange}
onTabClose={handleTabClose}
></NavBar>
{/*页面渲染*/}
{renderContent()} {renderContent()}
{/*底部日志栏*/}
{urlParams.identity !== 'componentDevelopment' && <LogBar></LogBar>} {urlParams.identity !== 'componentDevelopment' && <LogBar></LogBar>}
</div> </div>
</div> </div>

@ -0,0 +1,119 @@
import React, { useState, useEffect } from 'react';
import { Tabs } from '@arco-design/web-react';
import styles from './style/navbar.module.less';
const TabPane = Tabs.TabPane;
interface NavBarProps {
selected?: { currentPath?: string; currentKey?: string; };
menuData?: any[];
onTabChange?: (path: string) => void;
onTabClose?: (path: string) => void;
}
const NavBar: React.FC<NavBarProps> = ({ selected, menuData, onTabChange, onTabClose }) => {
const [tabs, setTabs] = useState<any[]>([]);
const [activeTab, setActiveTab] = useState<string>('');
// 根据菜单数据和路径查找菜单标题
const findMenuTitle = (menu: any[], path?: string): string => {
if (!path) return '未知页面';
for (const item of menu) {
if (item.path === path) {
return item.title;
}
if (item.children) {
const title = findMenuTitle(item.children, path);
if (title) return title;
}
}
return '未知页面';
};
// 当选中的菜单项变化时添加新的tab
useEffect(() => {
if (selected?.currentPath) {
const path = selected.currentPath;
// 检查tab是否已存在
const existingTab = tabs.find(tab => tab.path === path);
if (!existingTab) {
// 创建新tab
const title = menuData ? findMenuTitle(menuData, path) : path;
const newTab = {
key: path,
title: title,
path: path
};
setTabs(prev => [...prev, newTab]);
setActiveTab(path);
}
else {
// 如果tab已存在激活它
setActiveTab(path);
}
}
}, [selected, menuData]);
const handleDeleteTab = (key: string) => {
console.log("key:",key);
const newTabs = tabs.filter(tab => tab.key !== key);
setTabs(newTabs);
// 如果删除的是当前激活的tab激活第一个tab如果存在
if (key === activeTab && newTabs.length > 0) {
console.log("newTabs[0].key:",newTabs[0].key);
setActiveTab(newTabs[0].key);
onTabChange?.(newTabs[0].path);
}
else if (key === activeTab && newTabs.length === 0) {
setActiveTab('');
onTabChange?.('');
}
// 通知父组件tab已关闭
onTabClose?.(key);
};
const handleTabChange = (key: string) => {
setActiveTab(key);
// 查找对应的tab并通知父组件
const tab = tabs.find(t => t.key === key);
if (tab) {
onTabChange?.(tab.path);
}
};
return (
<div className={styles.navbar}>
{tabs.length > 0 ? (
<Tabs
editable
showAddButton={false}
type="card-gutter"
activeTab={activeTab}
onDeleteTab={handleDeleteTab}
onChange={handleTabChange}
>
{tabs.map(tab => (
<TabPane
destroyOnHide
key={tab.key}
title={tab.title}
>
</TabPane>
))}
</Tabs>
) : (
<div style={{ height: 40, display: 'flex', alignItems: 'center', paddingLeft: 20 }}>
</div>
)}
</div>
);
};
export default NavBar;

@ -19,14 +19,12 @@
position: relative; position: relative;
.mainContent { .mainContent {
display: flex;
flex-direction: column;
position: relative; position: relative;
flex: 1; flex: 1;
overflow: auto; overflow: auto;
padding: 16px;
> div {
height: 100%;
}
} }
} }
} }

@ -1,8 +1,7 @@
.logBar { .logBar {
width: calc(100% - 220px);
position: absolute; position: absolute;
bottom: 0; bottom: 0;
right: 0; left: 0;
background-color: #fff; background-color: #fff;
border-top: 2px solid #ddd; border-top: 2px solid #ddd;
transform: translateZ(0); transform: translateZ(0);

Loading…
Cancel
Save