OmniRoute — Design System & Visual Identity (中文 (简体))
营销网站(viral.omniroute.online、why.omniroute.online、omniroute.online)和产品仪表板应该看起来像同一个产品。网站已经从仪表板借用了其调色板 — 其 css/tokens.css 甚至写着 “调色板与 OmniRoute 仪表板(src/app/globals.css)保持一致”。因此,两者在颜色层面已经约有 80% 保持一致。仪表板目前缺少的是:
- 网站在每个页面中使用的方格纸网格壁纸。
- 网站已具备但仪表板缺少的一些共享设计 token(圆角比例、品牌渐变、
surface-2、等宽字体)。 - 组件级一致性 — 一些仪表板组件使用硬编码的十六进制值/rgba,绕过了主题 token。
本文档包含相关分析和实施计划。
- 唯一事实来源 =
src/app/globals.css。 网站应与仪表板保持同步,绝不能反过来。新 token 必须首先添加到globals.css。 - 只用 token,不用字面量。 组件使用语义化 token(
bg-surface、text-primary、border-border),绝不直接使用原始#hex。 - 低调,而非张扬。 网格是位于内容背后的淡化壁纸 — 它绝不能降低文本对比度,也不能干扰 UI。
- 感知主题。 所有内容在
.dark(产品的标志性外观)和浅色主题下均可正常使用。 - 渐进式发布。 先发布网格和 token(低风险、高可见度),然后分批清理组件。
3. 当前状态 — 已经对齐与尚未对齐的部分
Section titled “3. 当前状态 — 已经对齐与尚未对齐的部分”3.1 颜色 — 已统一 ✅
Section titled “3.1 颜色 — 已统一 ✅”每种品牌颜色和表面颜色在值层面均已与网站匹配(只有名称不同 — 仪表板使用 --color- 前缀)。已在 src/app/globals.css:30-128 中验证:
| 概念 | 网站 token(tokens.css) |
仪表板 token(globals.css) |
匹配情况 |
|---|---|---|---|
| 主色 | --primary #e54d5e |
--color-primary #e54d5e |
✅ |
| 主色悬停态 | --primary-hover #c93d4e |
--color-primary-hover #c93d4e |
✅ |
| 强调色 | --accent #6366f1 |
--color-accent #6366f1 |
✅ |
| 强调色 2 | --accent-2 #8b5cf6 |
--color-accent-hover #8b5cf6 |
✅(已重命名) |
| 强调色 3 | --accent-3 #a855f7 |
--color-accent-light #a855f7 |
✅(已重命名) |
| 成功 / 警告 / 错误 | #22c55e / #f59e0b / #ef4444 |
完全相同 | ✅ |
| 交通灯 | #ff5f56 / #ffbd2e / #27c93f |
完全相同 | ✅ |
| 深色背景 / 表面 / 边框 | #0b0e14 / #161b22 / rgba(255,255,255,.08) |
完全相同 | ✅ |
| 浅色背景 / 表面 / 文本 | #f9f9fb / #fff / #1a1a2e |
完全相同 | ✅ |
结论: 无需进行颜色迁移。视觉形象已经统一;我们是在对其进行_完善_,而不是重新构建。
3.2 差距 — 仪表板缺少的内容
Section titled “3.2 差距 — 仪表板缺少的内容”| 差异 | 站点现状 | 仪表盘现状 | 操作 |
|---|---|---|---|
| 网格壁纸 | body::before 方格纸效果、--grid-line、--grid-size 32px、--section-alt |
✅ 已添加(Phase 1) | Part A |
| 圆角尺度 | --radius 14px、--radius-sm 9px |
已添加 --radius 14px;-sm + 组件重新映射待完成 |
Part B / Phase 2 |
| 品牌渐变 | --grad-brand 135deg primary→accent-3 |
✅ 已添加令牌(Phase 1);将在 Phase 2 中使用 | Part B |
| 嵌套表面 | --surface-2 #1c2230 |
✅ 已添加(Phase 1) | Part B |
| 等宽字体 | --font-mono(ui-monospace 字体栈) |
待完成(Phase 4,与使用方一并处理) | Part B |
text-muted(深色) |
#8b8b9e |
#a1a1aa(zinc-400) |
协调统一 — Part B |
3.3 主题机制(确保不破坏任何功能)
Section titled “3.3 主题机制(确保不破坏任何功能)”- Tailwind v4,CSS 优先(无
tailwind.config.*)。令牌在:root/.dark中定义,并通过@theme inline暴露给工具类(globals.css:130-179)。 - 通过
<html>上的.dark类启用深色模式(globals.css:22中的@custom-variant dark),由自定义 Zustand store(src/store/themeStore.ts)切换,默认主题 =system(src/shared/constants/appConfig.ts:11)。站点改用html[data-theme="light"]——两种机制不同,但彼此不会相交(来源相互独立),因此不存在冲突。我们保留仪表盘的.dark机制。 - 支持运行时覆盖主色(
themeStore.ts:85-97,预设位于COLOR_THEMES)——用户可以替换--color-primary。任何引用--color-primary的新令牌(渐变等)都会自动继承这些覆盖。✅ - Tailwind v4 保留的圆角名称:
--radius-sm/md/lg/...是rounded-*工具类的底层变量。重新定义它们会追溯性地改变所有现有的rounded-*(例如,rounded-sm在 12 个文件中使用)。因此,小圆角值和组件重新映射有意推迟到 Phase 2,届时会与使用方一起修改。
4. A 部分 — 方格纸网格背景(核心诉求)— 已实现(阶段 1)
Section titled “4. A 部分 — 方格纸网格背景(核心诉求)— 已实现(阶段 1)”4.1 它是什么
Section titled “4.1 它是什么”来自网站(_mono_repo/omnirouteSite/css/base.css)的完整实现方案:一个固定、覆盖整个视口的伪元素,绘制两个 1px 线性渐变,并以 z-index:-1 位于所有内容之后。
body::before { content: ""; position: fixed; inset: 0; z-index: -1; pointer-events: none; background-image: linear-gradient(to right, var(--grid-line) 1px, transparent 1px), linear-gradient(to bottom, var(--grid-line) 1px, transparent 1px); background-size: var(--grid-size) var(--grid-size);}**为什么即使 body 设置了不透明的 background-color,这种方式仍然有效:**带有 z-index:-1 的 ::before 会绘制在元素自身背景的_上方_,但位于其正常文档流内容的_下方_。因此,--color-bg 作为基础填充色,网格叠加在其上,而应用内容则渲染在网格上方。
4.2 代码库中已有的先例
Section titled “4.2 代码库中已有的先例”src/app/landing/page.tsx:16-26 已经在单个页面中实现了相同的网格——但使用的是红色线条(#E54D5E,不透明度 0.06),网格尺寸为 50px,并带有动态光球。因此,这种模式已经在产品中得到验证;本项工作会将其提升为全局、主题感知的壁纸。
4.3 新增的令牌(位于 globals.css)
Section titled “4.3 新增的令牌(位于 globals.css)”:root { /* 浅色主题——相较网站使用的 0.045,提高了网格不透明度,从而确保壁纸 在内容密集的仪表板中确实可见(卡片和界面框架覆盖了视口的大部分区域) */ --grid-line: rgba(0, 0, 0, 0.07); --grid-size: 32px; --section-alt: rgba(0, 0, 0, 0.022);}.dark { /* 深色主题——出于相同原因,从 0.035 调高 */ --grid-line: rgba(255, 255, 255, 0.06); --section-alt: rgba(255, 255, 255, 0.018);}4.4 唯一的阻碍——已移除
Section titled “4.4 唯一的阻碍——已移除”该网格天然是全局的(它会一次性覆盖面板、auth/login、错误页面——即所有路由)。面板中恰好有一个元素遮住了它:
-
src/shared/components/layouts/DashboardLayout.tsx——最外层包装器绘制了不透明的bg-bg。其下方的所有元素本来就已经是透明的(<main>、滚动容器、内部的max-w-7xl),因此移除bg-bg后,body 网格便可透过内容区域显示出来(body 的--color-bg仍作为基础填充色)。<div className="flex h-dvh min-h-0 w-full overflow-hidden bg-bg"><div className="flex h-dvh min-h-0 w-full overflow-hidden">
4.5 界面框架交互(侧边栏 / 顶栏)
Section titled “4.5 界面框架交互(侧边栏 / 顶栏)”Header(Header.tsx:207,bg-bg)和Sidebar(Sidebar.tsx:430,bg-sidebar)保持不透明 → 网格仅显示在内容区域中,并由纯色界面框架包围。默认效果克制沉稳,与网站将界面框架和画布分隔开的方式一致(决策 D3 = 纯色)。
4.6 登录 / 身份验证 / 错误页面
Section titled “4.6 登录 / 身份验证 / 错误页面”这些页面直接渲染在 <body> 下(没有面板界面框架),因此全局网格应自动显示在它们后面。**阶段 5 — 已完成:**这些独立的全屏包装器实际上是不透明的(min-h-screen … bg-bg,其中 bg-bg 与 <body> 使用相同的纯色填充),这会遮住所有非仪表板页面上的网格,而不只是登录页面。现在它们全部改为透明,以便显示共享壁纸:login、forgot-password、callback、maintenance、offline、status、terms、privacy、onboarding 和 ErrorPageScaffold(覆盖 400/401)。这完成了 D4(从仅限登录页面扩展到所有独立页面)。由 tests/unit/design-grid-background.test.ts 提供保障。
4.7 落地页
Section titled “4.7 落地页”landing/page.tsx 保留其更丰富的动态背景(光球 + 暗角)——这是其专属的营销展示效果(决策 D5 = 保持不变)。
5. B 部分 — Token 统一
Section titled “5. B 部分 — Token 统一”阶段 1 添加惰性的、无冲突的标识 Token(--surface-2/--color-surface-2、--grad-brand、--radius)。阶段 2 将圆角尺度接入 Tailwind 并重新指向组件;阶段 4 添加 --font-mono 及其使用方。
| Token | 原因 | 阶段 |
|---|---|---|
--radius / --radius-sm |
使用统一的圆角尺度(14/9),而不是临时混用 6/8/12 | 1(值)/ 2(接入 + 重新指向) |
--grad-brand |
用于主要 CTA 的品牌渐变(红→紫),与站点保持一致 | 1(Token)/ 2(Button) |
--surface-2 |
嵌套面板 / 表头 / 内嵌行 | 1 |
--font-mono |
代码块、终端、ID、端点 | 4 |
--text-muted 协调 |
在站点↔面板之间选择一个值(推荐 #a1a1aa) |
2 |
D2(text-muted):站点为 #8b8b9e,仪表板为 #a1a1aa。建议保留仪表板的 #a1a1aa,并更新_站点_以保持一致。这属于外观调整。
6. C 部分 — 组件标准化(阶段 2–4)
Section titled “6. C 部分 — 组件标准化(阶段 2–4)”自定义组件(不使用 shadcn/Radix)、Tailwind v4,语义化 Token 大部分已采用(195 个文件导入共享桶文件)。工作重点是移除绕过机制。组件目录:src/shared/components/。
| # | 项目 | 文件 | 问题 → 目标 | 阶段 |
|---|---|---|---|---|
| C1 | 圆角对齐 | Button.tsx:14-18、Card.tsx:39、Modal.tsx、Input.tsx、Select.tsx |
混用 6/8/12px → --radius/--radius-sm(14/9) |
2 |
| C2 | 按钮渐变 + accent 变体 |
Button.tsx:5-12 |
主要按钮是纯红→红;改为与 --grad-brand 对齐;添加缺失的 accent 变体。约 195 个导入方——可见度最高 |
2 |
| C3 | 表格 | DataTable.tsx:122-176、logTableStyles.ts、globals.css:405-414 |
100% 使用内联硬编码 rgba + 不存在的变量;迁移到 Token,并淘汰不一致的样式 | 3 |
| C4 | 集中管理状态颜色 | flow/edgeStyles.ts、TokenHealthBadge.tsx、DegradationBadge.tsx、ProviderCascadeNode.tsx、Badge.tsx + 5 个辅助模块 |
同一十六进制颜色有 6+ 份副本 → 基于 --color-success/warning/error 的单一模块 |
3 |
| C5 | 卡片边框 | Card.tsx:39 |
border-white/5 → 品牌色 /8 |
2 |
| C6 | 协调焦点环 ✅ 已完成 | globals.css 中的 --focus-ring(强调色)与表单控件的 ring-primary/30 |
统一为强调色(紫色),以匹配全局焦点环,并与红色错误环明确区分;错误状态仍为红色 | 4 |
| C7 | 添加 Checkbox + Textarea |
带有内联 accentColor:#6366f1 的原始 <input>/<textarea> |
Token 驱动的基础组件 | 4 |
| C8 | 清理硬编码十六进制颜色 | ConsoleLogViewer.tsx:240、ComboLiveStudio.tsx:306、Modal 圆点、约 14 个图表文件 |
字面值 → Token | 4 |
| C9 | cn() → clsx + tailwind-merge |
src/shared/utils/cn.ts |
冲突类会叠加;C1 覆盖需要此项 | 2 |
已符合品牌规范(由 Token 驱动,仅需调整圆角):Badge、Toggle、SegmentedControl、Input、Select。
7. 发布计划
Section titled “7. 发布计划”- 阶段 1 — 网格 + 品牌标识令牌(本 PR)。
globals.css网格 +--surface-2/--grad-brand/--radius令牌;body::before壁纸;移除bg-bg阻碍项;静态防护测试。风险低,可通过一个提交回滚。 - 阶段 2 — 基础组件(C1、C2、C5)— 已在本 PR 中完成。 通过
@theme添加语义化圆角工具类rounded-card(14px) /rounded-control(9px)(使用自定义名称,因此默认的rounded-sm/md/lg/xl保持不变——不会引发波及 400 个文件的大规模修改);Card/Modal → 14px,Button/Input/Select → 9px;Button 主按钮 →--grad-brand(红色→紫色)+ 新增accent变体;Card 边框 →border-border令牌 (0.08)。已推迟:cn()→tailwind-merge (C9) 需要新增依赖;临时性的rounded-lg全面清理(326 个文件)维持原状,因为基础组件已覆盖大部分界面。 - 阶段 3 — 状态颜色 + 表格(C3、C4)— 已在本 PR 中完成。 ✅ C4(
src/shared/constants/statusColors.ts— 以STATUS_HEX作为单一来源;flow/edgeStyles.ts+TokenHealthBadge已改为引用它,表现一致/十六进制值相同)。✅--font-mono令牌。✅ C3 (DataTable) — 使用一组--table-*令牌(--table-header-bg/-row-zebra/-row-hover/-cell-border/-row-selected)替换了所有内联 rgba,以及无效的var(--bg-table-header)/var(--text-secondary)回退值;其深色模式值与旧的硬编码 rgba 完全相同(深色模式逐字节一致),而浅色模式值修复了此前始终呈现深色的问题。表头边框 →--color-border,次要文本 →--color-text-muted。合并前需要进行一次视觉检查。(未触及:logTableStyles.ts和旧版 Ant.ant-table规则——这些将单独处理,优先级较低。) - 阶段 4 — 清理(C6、C7、C9 已完成;C8 待完成)。 ✅ C9
cn()→twMerge(clsx(...))(已将 clsx + tailwind-merge 添加为依赖)——调用方的className现在会正确地_替换_基础组件中冲突的类,而不是将它们叠加。✅ C7 新增Checkbox+Textarea基础组件(由令牌驱动,并从桶文件导出;属于增量添加——后续可逐步采用,以替换 32 个原生复选框 / 41 个原生文本区域)。✅ C6 焦点环协调——表单控件(Input/Select/Textarea/Toggle/Checkbox)现在聚焦时使用**强调色(紫色)**焦点环,以匹配全局--focus-ring,并避免与红色错误环冲突;红色错误状态保持不变。⏳ C8 十六进制颜色清理并非盲目的查找/替换——已确认以下问题项是_有意如此_且必须保留:ConsoleLogViewer.tsx:240(始终为深色的终端)、TokenHealthBadge弹出框、ReactFlow SVG 描边。仅迁移确实需要感知主题的十六进制颜色。
每个阶段:npm run lint + npm run typecheck:core + 一次视觉检查。
8. 待定事项(建议)
Section titled “8. 待定事项(建议)”- D1 — Button 主按钮: 保持红色→红色,还是切换为红色→紫色
--grad-brand?建议:红色→紫色(阶段 2)。 - **D2 — 网格线颜色:**中性色(站点风格)——已选定——而非品牌红色。尺寸为 32px(根据负责人的反馈,相较原始的 46px 缩小约 30%——46px 的网格单元在仪表盘布局中显得过大)。
- D3 — 界面框架鲜艳度: 侧边栏/页眉使用纯色——已选定。
- D4 — 认证/登录网格: ✅ 已完成(阶段 5)——已从每个独立的全屏包装器中移除不透明的
bg-bg(而不只是登录页),因此所有屏幕上都能显示网格。参见 §4.6。 - D5 — 落地页: 保持动画启动画面不变。已选定。
- D6 — 全产品统一使用 14/9 圆角: 建议:是(阶段 2)。
- D7 — 阶段 1 优先发布: 已选定。
- D8 — 布局宽度(阶段 5): 仪表盘内容外壳此前限制为
max-w-7xl(1280px),导致其在大型显示器上居中显示,两侧留有较宽的空白边距。✅ 已完成——已提升为流式max-w-[3840px](真正的 4K):内容现在会随视口扩展至约 4K,仅在超过该宽度后居中(DashboardLayout.tsx)。有意保持较窄的页面仍按设计维持窄幅(ProviderOnboardingWizardmax-w-5xl,Rtk/CavemanContextPageClientmax-w-6xl)。 - D9 — 不透明数据表格(阶段 6): 仪表盘内容区域现已透明(因此网格壁纸可以透出,阶段 5),但若数据表格的容器不是不透明表面,网格就会透过其透明偶数行 / 低透明度斑马纹显示出来。✅ 已完成——现在所有不在卡片内的表格都会绘制
bg-surface(对于<DataTable>基础组件,则在其滚动容器上设置background: var(--color-surface))。已修复:DataTable(基础组件)、ProxyLogger/RequestLoggerV2(其<Card>的bg-black/5 dark:bg-black/20色调通过 tailwind-merge 覆盖了 Card 的bg-surface→ 约 95% 透明)、BatchListTab/FilesListTab/CacheEntriesTab/ReasoningCacheTab/cache page/FreePoolTab/ModelMappingTable/HeaderTable,以及缓存视图中的两个 CSS 网格“表格”(bg-surface/35→bg-surface)。经验证,已位于<Card>/Modal 内的表格是不透明的,因此有意保持不变(在这些位置添加 bg-surface 只是无实际作用的冗余操作)。网格本身无需更改——仪表盘的body::before与站点逐字节一致(--grid-size: 32px);运行实例中出现的任何“更大网格”都是#4143之前的陈旧构建,而非代码问题。由tests/unit/design-grid-background.test.ts提供防护(阶段 6 区块)。
9. 范围外事项 / 风险
Section titled “9. 范围外事项 / 风险”- 不更改调色板 — 现有颜色已匹配;我们只补充缺失的令牌。产品不会出现重新着色的风险。
- 不更改主题引擎 — 保留
.dark+ Zustand store。 - 圆角调整(阶段 2)影响范围广 — 会涉及每个卡片/按钮/输入框;合并前需目视检查内容繁多的界面(表格、模态框)。
- **表格(C3)**包含最多的硬编码样式,回归风险范围也最大 — 应放在独立的 PR 中处理。
10. 参考索引
Section titled “10. 参考索引”| 区域 | 路径 |
|---|---|
| 仪表板令牌 | src/app/globals.css(:root、.dark、@theme inline、body、body::before) |
| 主题 store | src/store/themeStore.ts、src/shared/components/ThemeProvider.tsx、src/shared/constants/appConfig.ts:9-11 |
| 面板外壳(在此解除网格阻塞) | src/shared/components/layouts/DashboardLayout.tsx |
| 框架 UI | src/shared/components/Header.tsx:207、src/shared/components/Sidebar.tsx:430 |
| 网格先例 | src/app/landing/page.tsx:16-26 |
| 基础组件 | src/shared/components/{Button,Card,Input,Select,Badge,Modal,Toggle,SegmentedControl,Loading,Tooltip,DataTable}.tsx |
| 状态颜色来源 | flow/edgeStyles.ts、TokenHealthBadge.tsx、DegradationBadge.tsx、logTableStyles.ts |
cn 工具 |
src/shared/utils/cn.ts |
| 阶段 1 防护测试 | tests/unit/design-grid-background.test.ts |
| 站点参考 | _mono_repo/omnirouteSite/css/tokens.css、css/base.css |
HagiCode
HagiCode 是一套智能体编码工作台:结构化工作流、多 Agent 并行执行与 Hero Dungeon 视图,把想法变成真正交付的软件。
让想法更快变成好用的软件,让智能编码更聪明、更高效,也更有趣。

- Smart结构化工作流将意图转化为从想法到交付的可执行路径。
- Efficient多 Agent 工作流让调研、实现与审阅并行推进。
- FunHero Dungeon 让长时间编码协作更直观、更有参与感。