feat: DevTools 侧边栏分类折叠 — 5 个可折叠分组 + 高度自适应展开
- 仪表盘独立在外,其余 14 个面板分为 AI 认知/系统运维/工具插件/通信平台/模型 5 组 - 屏幕高度 >= 900px 自动展开,< 900px 折叠 - 侧边栏折叠模式强制展开分组以保持 icon-only 可用 - 使用原生 details/summary 元素,零依赖 Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
+115
-49
@@ -35,8 +35,10 @@ body {
|
||||
overflow: hidden; z-index: 10;
|
||||
}
|
||||
#sidebar.collapsed { width: var(--sidebar-collapsed); }
|
||||
#sidebar.collapsed .nav-label, #sidebar.collapsed .sidebar-title, #sidebar.collapsed .sidebar-footer-text { display: none; }
|
||||
#sidebar.collapsed .nav-label, #sidebar.collapsed .sidebar-title, #sidebar.collapsed .sidebar-footer-text,
|
||||
#sidebar.collapsed .nav-group > summary { display: none; }
|
||||
#sidebar.collapsed .nav-item { justify-content: center; padding: 10px 0; }
|
||||
#sidebar.collapsed .nav-group > .nav-item { padding-left: 0; }
|
||||
#sidebar.collapsed .nav-icon { margin-right: 0; }
|
||||
|
||||
.sidebar-header {
|
||||
@@ -71,6 +73,29 @@ body {
|
||||
border-radius: 10px; font-weight: 600; display: none;
|
||||
}
|
||||
|
||||
/* 侧边栏分类折叠组 */
|
||||
.nav-group {
|
||||
border: none; margin: 0; padding: 0;
|
||||
}
|
||||
.nav-group > summary {
|
||||
display: flex; align-items: center; gap: 8px;
|
||||
padding: 6px 12px 4px; border-radius: var(--radius-sm);
|
||||
cursor: pointer; color: var(--text3); font-size: 10px; font-weight: 700;
|
||||
text-transform: uppercase; letter-spacing: 0.06em;
|
||||
list-style: none; user-select: none; transition: all var(--transition);
|
||||
}
|
||||
.nav-group > summary::-webkit-details-marker { display: none; }
|
||||
.nav-group > summary::marker { display: none; content: none; }
|
||||
.nav-group > summary:hover { background: var(--bg3); color: var(--text2); }
|
||||
.nav-group > summary .group-arrow {
|
||||
margin-left: auto; font-size: 9px; transition: transform var(--transition); opacity: 0.6;
|
||||
}
|
||||
.nav-group[open] > summary .group-arrow { transform: rotate(90deg); }
|
||||
.nav-group > .nav-item { padding-left: 28px; }
|
||||
|
||||
#sidebar.collapsed .nav-group > summary,
|
||||
#sidebar.collapsed .nav-group > .nav-item { padding-left: 0; }
|
||||
|
||||
.sidebar-footer {
|
||||
padding: 12px 16px; border-top: 1px solid var(--border);
|
||||
display: flex; align-items: center; gap: 8px;
|
||||
@@ -285,8 +310,10 @@ input[type="range"] { accent-color: var(--accent); padding: 0; }
|
||||
@media (max-width: 900px) {
|
||||
.cards-2, .cards-3, .cards-4 { grid-template-columns: 1fr; }
|
||||
#sidebar { width: var(--sidebar-collapsed); }
|
||||
#sidebar .nav-label, #sidebar .sidebar-title, #sidebar .sidebar-footer-text { display: none; }
|
||||
#sidebar .nav-label, #sidebar .sidebar-title, #sidebar .sidebar-footer-text,
|
||||
#sidebar .nav-group > summary { display: none; }
|
||||
#sidebar .nav-item { justify-content: center; padding: 10px 0; }
|
||||
#sidebar .nav-group > .nav-item { padding-left: 0; }
|
||||
#sidebar .nav-icon { margin-right: 0; }
|
||||
}
|
||||
|
||||
@@ -652,53 +679,73 @@ input[type="range"] { accent-color: var(--accent); padding: 0; }
|
||||
<button class="nav-item active" data-panel="dashboard">
|
||||
<span class="nav-icon">🏠</span><span class="nav-label">仪表盘</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="memory">
|
||||
<span class="nav-icon">🧠</span><span class="nav-label">记忆管理</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="sessions">
|
||||
<span class="nav-icon">💬</span><span class="nav-label">会话监看</span>
|
||||
<span class="nav-badge" id="sessions-badge">0</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="services">
|
||||
<span class="nav-icon">🖥</span><span class="nav-label">服务管理</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="performance">
|
||||
<span class="nav-icon">📊</span><span class="nav-label">性能监控</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="iot">
|
||||
<span class="nav-icon">🏠</span><span class="nav-label">IoT 设备</span>
|
||||
<span class="nav-badge" id="iot-badge" style="display:none">0</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="toolCalls">
|
||||
<span class="nav-icon">🔧</span><span class="nav-label">工具调用</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="stt">
|
||||
<span class="nav-icon">🎤</span><span class="nav-label">语音识别</span>
|
||||
<span class="nav-badge" id="stt-badge" style="display:none">0</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="database">
|
||||
<span class="nav-icon">🗄️</span><span class="nav-label">数据库监看</span>
|
||||
<span class="nav-badge" id="db-badge" style="display:none">●</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="thinking">
|
||||
<span class="nav-icon">💭</span><span class="nav-label">自主思考</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="timeline">
|
||||
<span class="nav-icon">⏱️</span><span class="nav-label">记忆时间线</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="chatPlatforms">
|
||||
<span class="nav-icon">💬</span><span class="nav-label">第三方聊天</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="clients">
|
||||
<span class="nav-icon">📱</span><span class="nav-label">客户端管理</span>
|
||||
<span class="nav-badge" id="clients-badge" style="display:none">0</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="modelConfig">
|
||||
<span class="nav-icon">🤖</span><span class="nav-label">模型配置</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="llmCalls">
|
||||
<span class="nav-icon">📊</span><span class="nav-label">LLM 调用</span>
|
||||
</button>
|
||||
|
||||
<details class="nav-group">
|
||||
<summary>🧠<span style="flex:1">AI 认知</span><span class="group-arrow">▶</span></summary>
|
||||
<button class="nav-item" data-panel="memory">
|
||||
<span class="nav-icon">🧠</span><span class="nav-label">记忆管理</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="sessions">
|
||||
<span class="nav-icon">💬</span><span class="nav-label">会话监看</span>
|
||||
<span class="nav-badge" id="sessions-badge">0</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="thinking">
|
||||
<span class="nav-icon">💭</span><span class="nav-label">自主思考</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="timeline">
|
||||
<span class="nav-icon">⏱️</span><span class="nav-label">记忆时间线</span>
|
||||
</button>
|
||||
</details>
|
||||
|
||||
<details class="nav-group">
|
||||
<summary>⚙️<span style="flex:1">系统运维</span><span class="group-arrow">▶</span></summary>
|
||||
<button class="nav-item" data-panel="services">
|
||||
<span class="nav-icon">🖥</span><span class="nav-label">服务管理</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="performance">
|
||||
<span class="nav-icon">📊</span><span class="nav-label">性能监控</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="database">
|
||||
<span class="nav-icon">🗄️</span><span class="nav-label">数据库监看</span>
|
||||
<span class="nav-badge" id="db-badge" style="display:none">●</span>
|
||||
</button>
|
||||
</details>
|
||||
|
||||
<details class="nav-group">
|
||||
<summary>🔧<span style="flex:1">工具 & 插件</span><span class="group-arrow">▶</span></summary>
|
||||
<button class="nav-item" data-panel="iot">
|
||||
<span class="nav-icon">🏠</span><span class="nav-label">IoT 设备</span>
|
||||
<span class="nav-badge" id="iot-badge" style="display:none">0</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="toolCalls">
|
||||
<span class="nav-icon">🔧</span><span class="nav-label">工具调用</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="stt">
|
||||
<span class="nav-icon">🎤</span><span class="nav-label">语音识别</span>
|
||||
<span class="nav-badge" id="stt-badge" style="display:none">0</span>
|
||||
</button>
|
||||
</details>
|
||||
|
||||
<details class="nav-group">
|
||||
<summary>💬<span style="flex:1">通信平台</span><span class="group-arrow">▶</span></summary>
|
||||
<button class="nav-item" data-panel="chatPlatforms">
|
||||
<span class="nav-icon">💬</span><span class="nav-label">第三方聊天</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="clients">
|
||||
<span class="nav-icon">📱</span><span class="nav-label">客户端管理</span>
|
||||
<span class="nav-badge" id="clients-badge" style="display:none">0</span>
|
||||
</button>
|
||||
</details>
|
||||
|
||||
<details class="nav-group">
|
||||
<summary>🤖<span style="flex:1">模型</span><span class="group-arrow">▶</span></summary>
|
||||
<button class="nav-item" data-panel="modelConfig">
|
||||
<span class="nav-icon">🤖</span><span class="nav-label">模型配置</span>
|
||||
</button>
|
||||
<button class="nav-item" data-panel="llmCalls">
|
||||
<span class="nav-icon">📊</span><span class="nav-label">LLM 调用</span>
|
||||
</button>
|
||||
</details>
|
||||
</nav>
|
||||
<div class="sidebar-footer">
|
||||
<span id="ws-dot" class="disconnected"></span>
|
||||
@@ -997,8 +1044,27 @@ document.querySelectorAll('.nav-item').forEach(btn => {
|
||||
document.getElementById('toggle-sidebar').addEventListener('click', () => {
|
||||
STATE.sidebarCollapsed = !STATE.sidebarCollapsed;
|
||||
document.getElementById('sidebar').classList.toggle('collapsed', STATE.sidebarCollapsed);
|
||||
// 折叠侧边栏时强制展开所有分组,否则 icon-only 模式看不到菜单项
|
||||
if (STATE.sidebarCollapsed) {
|
||||
document.querySelectorAll('.nav-group').forEach(g => g.setAttribute('open', ''));
|
||||
} else {
|
||||
autoExpandGroups(); // 恢复高度判断
|
||||
}
|
||||
});
|
||||
|
||||
// 侧边栏分组自动展开/折叠 — 屏幕高度 >= 900px 时自动展开
|
||||
function autoExpandGroups() {
|
||||
const groups = document.querySelectorAll('.nav-group');
|
||||
if (groups.length === 0) return;
|
||||
const expand = window.innerHeight >= 900;
|
||||
groups.forEach(g => {
|
||||
if (expand) g.setAttribute('open', '');
|
||||
else g.removeAttribute('open');
|
||||
});
|
||||
}
|
||||
window.addEventListener('resize', autoExpandGroups);
|
||||
autoExpandGroups();
|
||||
|
||||
function switchPanel(name) {
|
||||
STATE.activePanel = name;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user