// Workspace shell: top bar + sidebar + tabs + screen routing. const Workspace = ({ session, onLogout }) => { const [users, setUsers] = React.useState(() => XLY.buildUsers()); const [expanded, setExpanded] = React.useState({ kpi: true, quote: true, sys: true }); const [searchQ, setSearchQ] = React.useState(""); const [activeNodeId, setActiveNodeId] = React.useState("home"); const [sidebarOpen, setSidebarOpen] = React.useState(true); const [tabs, setTabs] = React.useState([ { id: "home", label: "主页", screen: "home", icon: "home", closable: false }, ]); const [activeTabId, setActiveTabId] = React.useState("home"); const [megaOpen, setMegaOpen] = React.useState(false); const openTab = (tab) => { setTabs((ts) => ts.find((t) => t.id === tab.id) ? ts : [...ts, tab]); setActiveTabId(tab.id); }; const closeTab = (id) => { setTabs((ts) => { const i = ts.findIndex((t) => t.id === id); const next = ts.filter((t) => t.id !== id); if (id === activeTabId) { const fallback = next[Math.max(0, i - 1)] || next[0]; if (fallback) setActiveTabId(fallback.id); } return next; }); }; const onNodeClick = (node) => { setActiveNodeId(node.id); if (node.screen === "userlist") openTab({ id: "userlist", label: "用户列表", screen: "userlist" }); else if (node.screen === "module") openTab({ id: "module", label: "系统模块配置", screen: "module" }); else if (node.id === "home") openTab({ id: "home", label: "主页", screen: "home", closable: false }); else if (node.id === "quote-01") openTab({ id: "module", label: "系统模块配置", screen: "module" }); else openTab({ id: node.id, label: node.label, screen: "stub", stubLabel: node.label }); }; const openUserDetail = (user, mode = "view") => { const id = `user-${user.id}`; const label = `用户信息单据 · ${user.employee}`; setTabs((ts) => { if (ts.find((t) => t.id === id)) return ts; return [...ts, { id, label, screen: "userdetail", userId: user.id, mode }]; }); setActiveTabId(id); }; const createUser = () => { const newU = { id: `new-${Date.now()}`, seq: users.length + 1, employee: "", empNo: "", account: "", department: "", type: "普通用户", language: "中文", disabled: false, lastLogin: "", createdBy: session.user, createdAt: new Date().toISOString().slice(0, 19).replace("T", " "), permissions: XLY.PERMISSION_GROUPS.reduce((a, g) => (a[g] = false, a), {}), tabPerms: {}, }; setUsers((us) => [...us, newU]); openUserDetail(newU, "new"); }; const saveUser = (u) => setUsers((us) => us.map((x) => x.id === u.id ? u : x)); const activeTab = tabs.find((t) => t.id === activeTabId); return (
{/* Top bar */}
XLY-ERP · {session.company}
{/* Tab strip */} {/* Body */}
{sidebarOpen && activeTabId === "home" ? (
) : null}
{activeTab ? openTab({ id: s, label, screen: s })} /> : null}
{/* Status bar */}
就绪 · 当前用户 {session.user} · {session.company} XLY-ERP v8.6.2 · © 2017–2026 XLY 软件股份
{megaOpen ? ( setMegaOpen(false)} onOpen={(screen, label) => openTab({ id: screen, label, screen })} /> ) : null}
); }; const ScreenRouter = ({ tab, users, onOpenUser, onCreateUser, onSaveUser, session, onOpenScreen }) => { if (tab.screen === "home") return ; if (tab.screen === "userlist") return ; if (tab.screen === "module") return ; if (tab.screen === "userdetail") { const u = users.find((x) => x.id === tab.userId); if (!u) return 用户不存在; return ; } return {tab.stubLabel || tab.label} · 模块开发中; }; const Empty = ({ children }) => (
{children}
); const topBtn = { display: "inline-flex", alignItems: "center", gap: 5, height: 28, padding: "0 10px", background: "transparent", color: "var(--text-on-dark)", border: "none", cursor: "pointer", fontSize: 12, }; window.Workspace = Workspace;