40 KiB
GoodBuddy 统一界面设计系统
1. 目的与适用范围
本文定义 GoodBuddy 桌面端的统一界面规则,适用于聊天与最近对话、知识库、智能心跳、任务与活动记录,以及后续新增的一级页面。
设计系统解决两类问题:
- 统一跨页面的视觉语言、信息层级和交互反馈。
- 保留不同工作场景所需的布局差异,不强行把阅读、工作台、仪表盘和数据视图做成同一种页面。
所有新界面必须优先使用本文定义的语义令牌、页面壳层和共享组件。现有界面迁移时应保持功能与数据语义不变,不以视觉统一为理由隐藏范围、状态或风险。
2. 核心原则
2.1 一致的语义,不要求相同的布局
- 相同含义使用相同的颜色、间距、控件和文案结构。
- 不同任务使用明确命名的页面壳层,不再为单个页面随意设置宽度。
- 页签只用于同级页面导航,分段控件只用于当前视图内的单选切换,筛选控件只改变当前数据集合。
2.2 范围始终可见
知识、任务、自动化和活动记录可能属于全局或某个项目。当前范围必须在页面标题区或对象标题旁持续显示,不能只通过入口位置、默认筛选或颜色暗示。
2.3 主任务优先
- 每个页面只保留一个视觉上最突出的主操作。
- 页面标题、范围、说明、主操作和导航按固定层级排列。
- 次要设置、筛选和批量操作不得与主任务争夺注意力。
2.4 状态明确且可恢复
- 加载、空内容、无结果、失败、只读和权限不足是不同状态,必须分别呈现。
- 可撤销操作优先提供撤销,不可撤销操作必须在执行前说明影响范围。
- 不依赖颜色单独表达状态或风险。
2.5 默认支持浅色与深色主题
组件不得直接使用原始颜色值。主题差异只在令牌层定义,业务组件仅引用语义令牌。
两种主题必须保持相同的信息层级,但不要求机械地反转明暗。浅色主题以白色主内容画布、冰蓝灰侧栏和轻微着色的顶栏建立空间关系;深色主题使用深海军蓝与蓝灰表面逐层提亮,避免纯黑。蓝色承担主要选择和交互,青绿色主要承担成功与可用状态,二者不得混用语义。
3. 设计令牌
令牌以 CSS 自定义属性实现。:root 提供浅色值,[data-theme="dark"] 覆盖深色值。组件样式不得新增只服务于单个页面的颜色、阴影、圆角或间距常量。
3.1 颜色令牌
| 令牌 | 用途 |
|---|---|
--surface-canvas |
应用和页面底色 |
--surface-raised |
卡片、面板、输入框和弹窗 |
--surface-subtle |
次级区域和控件底色 |
--surface-muted |
进度轨道和更弱的分隔表面 |
--text-primary |
标题与主要正文 |
--text-secondary |
辅助正文 |
--text-muted |
占位、时间和弱提示 |
--text-on-accent |
强调色或危险色表面上的文字 |
--border-default |
常规边框 |
--border-control |
输入框、分段控件等必须清晰可辨的控件边界 |
--border-subtle |
区块分隔线 |
--accent、--accent-hover |
强调文字、图标和交互反馈 |
--accent-solid、--accent-solid-hover |
主按钮等需要反白文字的强调背景 |
--accent-selected、--accent-subtle |
选中边框、选中背景和信息强调 |
--success、--success-subtle |
成功状态 |
--warning |
警告状态 |
--danger、--danger-strong |
危险文本和状态 |
--danger-solid |
最终确认按钮等需要反白文字的危险背景 |
--danger-border、--danger-subtle |
危险入口和失败状态背景 |
浅色与深色具体值只在 styles.css 的主题根节点维护。状态组件必须同时显示文字或图标,不能仅靠颜色区分。
表面与边框使用规则:
- 浅色主题的阅读、编辑和页面主内容使用白色或接近白色的
--surface-raised;主侧栏使用更深一阶的冰蓝灰--surface-canvas,顶栏使用弱于侧栏的次级表面。相邻区域必须可辨,但不能形成高饱和色块。 - 深色主题从深海军蓝画布开始,以蓝灰表面逐层提亮。不同层级优先依靠表面亮度与语义边框区分,不使用纯黑底色或无边界的大面积同色区域。
- 浅色侧栏中,导航与最近会话、最近会话与账户区之间的结构分隔线使用
--border-default。列表行之间或卡片内部的弱分隔仍使用--border-subtle,不得为了增强结构而给每一项加重边框。 - 控件边界、焦点环和选中边框必须达到至少
3:1的非文本对比度;正文、状态色和弱文本分别遵守无障碍对比度要求。 - 业务组件不得通过主题条件分支写原始颜色;新增视觉层级时先确认能否复用现有表面、边框和状态令牌。
3.2 间距令牌
采用 4 像素基准:
| 令牌 | 值 | 典型用途 |
|---|---|---|
--space-0 |
0 |
显式取消间距 |
--space-1 |
4px |
图标内部微调 |
--space-2 |
8px |
紧凑控件、图标与文字 |
--space-3 |
12px |
表单字段内部、紧凑列表 |
--space-4 |
16px |
默认组件间距 |
--space-6 |
24px |
区块间距、窄屏页面内边距 |
使用规则:
- 同一组件内部优先使用
8px、12px、16px。 - 同一区块内组件之间优先使用
16px或24px。 - 页面级区块之间优先使用
32px或40px。 - 不新增
14px、18px、22px等非令牌间距。
3.3 字体令牌
界面默认使用随客户端本地打包的 Inter Variable 与 Noto Sans SC Variable:英文、数字优先使用 Inter,简体中文由 Noto Sans SC 覆盖。系统无衬线字体仅作为启动和缺失字形回退;代码、标识符和原始日志使用等宽字体栈。字体不得通过运行时网络请求加载。
| 令牌 | 字号 / 行高 | 字重 | 用途 |
|---|---|---|---|
--font-caption |
11px |
时间、短标签和紧凑元数据 | |
--font-body |
13px |
默认界面正文 | |
--font-section-title |
14px |
卡片和区块标题 | |
--font-page-title |
24px |
一级页面标题 |
使用规则:
- 业务组件通过
--font-family-ui与字体尺寸令牌继承字体,不创建页面专属字体栈。 - 表单按钮、输入框、选择框和文本域必须继承界面字体,避免回退为原生控件字体。
- 连续阅读内容使用
14px,持久辅助信息不得小于11px。 - 本地字体资源必须随生产包交付,并同时包含 Inter 与 Noto Sans SC 的 OFL 许可证。
- 页面内不得通过同时放大字号、加粗和使用强调色制造多个同级主标题。
3.4 圆角、阴影与层级
| 令牌 | 值 | 用途 |
|---|---|---|
--radius-control |
10px |
输入框、按钮、菜单项 |
--radius-card |
14px |
卡片和面板 |
--shadow-card |
主题定义 | 卡片和选中分段控件 |
--shadow-dialog |
主题定义 | 对话框和浮层 |
整体使用适度圆角:控件和卡片保持清晰、克制的几何轮廓,不使用胶囊化的大圆角替代信息层级。普通卡片通过表面色和边框区分,不默认添加阴影;输入区等需要从内容流中明确浮起的持续操作面板可以使用克制的 --shadow-card。菜单和对话框使用对应层级阴影,阴影只表示真实的浮层关系。不允许页面自行创建高于 --z-dialog 的层级。
3.5 动效令牌
--motion-fast: 120ms:悬停、按压、焦点反馈。--motion-normal: 180ms:菜单、折叠区域、轻量视图切换。--motion-slow: 240ms:对话框和抽屉。- 默认缓动使用
ease-out,退出可使用ease-in。 - 在
prefers-reduced-motion: reduce下移除非必要位移和缩放,仅保留即时状态切换。
4. 页面壳层
所有一级页面使用 PageShell。壳层负责水平居中、最大宽度、响应式内边距、页面背景和滚动边界,业务页面不得再次设置独立的整体最大宽度。
| 变体 | 最大内容宽度 | 适用场景 | 页面映射 |
|---|---|---|---|
reading |
820px |
连续阅读、单列编辑、对话撰写 | 聊天正文与输入区 |
standard |
960px |
常规列表、设置、表单与任务管理 | 最近对话、任务 |
dashboard |
1040px |
指标、卡片网格、宽表格与审计数据 | 智能心跳、活动记录 |
master-detail |
可用空间内流式铺开 | 左侧选择、右侧编辑或预览 | 知识库 |
共同规则:
- 宽度计算统一为
min(100%, 变体最大宽度)。 - 页面左右内边距在常规桌面窗口为
32px,中等窗口为24px,窄窗口为16px。 - 页面顶部和底部内边距默认为
32px。 master-detail的左栏建议为280px至360px,右栏占剩余空间。分隔线和滚动容器属于壳层,不由内容卡片模拟。- 聊天输入区可以粘附在
reading壳层底部,但消息内容和输入区必须共享同一阅读宽度。 - 宽表格可在
dashboard内容区内部横向滚动,不得撑宽整个应用窗口。
5. 信息层级
一级页面按以下顺序组织:
PageHeaderPageTabs,仅在存在同级子页面时出现- 页面级状态或重要提示
- 筛选与批量操作工具栏
- 主内容
- 与主内容就近关联的分页或加载状态
一个页面只能有一个可见的一级标题。卡片标题不得重复页面标题。面包屑只在层级超过两级且返回关系无法通过侧栏或主从布局表达时使用。
5.1 PageHeader
PageHeader 统一接收以下内容:
title:必填,简短名词或任务名称。description:可选,一行说明当前页面能做什么,不重复标题。scope:涉及范围的数据页面必填,使用ScopeBadge。primaryAction:可选,页面唯一主操作。secondaryActions:可选,最多两个直接显示,其余进入更多菜单。status:可选,用于只读、同步中、连接异常等页面级状态。
布局规则:
- 标题和范围徽标在同一信息组中,范围不得放入更多菜单。
- 主操作位于标题区右侧,窄窗口下换行到标题下方并保持靠左。
- 不在内容卡片中再次渲染同名标题。
- 标题区默认不粘附。只有主内容长且页面级操作需要持续可用时才启用粘附。
6. 共享组件
6.1 PageTabs
用于同一一级页面内的同级内容面板,例如心跳的“成长概览”和“心跳计划”。
- 使用
tablist、tab和tabpanel语义,当前项使用aria-selected="true"。 - 一级页面之间的导航由应用主导航承担,不复用
PageTabs。 - 标签保持短名词,不显示句号,不用页签承载开关或过滤条件。
- 项目过多时优先重组信息架构,不把一级页签做成多行。
PageTabs可使用默认视觉或共享的segmented视觉变体。紧凑主从工作台中的 2 至 4 个同级面板可使用与模型设置一致的分段外观,但不得因此改用按钮组语义。- 视觉变体不改变组件含义:分段外观的
PageTabs仍使用页签语义、单一激活面板、游标焦点和方向键切换,不复制页面专属样式。
6.2 SegmentedControl
用于当前页面内互斥的视图或状态切换,例如“列表 / 网格”或少量单选状态。
- 选项数量为 2 至 4 个。
- 使用带
aria-pressed的按钮组语义,支持方向键切换。 - 不能用于多选筛选、页面导航或执行即时命令。
- 控件宽度由内容决定,除移动窄屏外不默认等分整行。
6.3 筛选工具栏
筛选不创建第五种类似页签的视觉控件:
- 2 至 4 个互斥状态可使用
SegmentedControl。 - 多维条件使用统一尺寸的选择框、搜索框和复选菜单。
- 已生效条件以文字和值明确展示,并提供“清除筛选”。
- 无匹配结果使用“无结果”状态,不能显示为首次使用的空状态。
- 筛选条件改变数据范围时,结果数量或当前条件必须可见。
6.4 ScopeBadge
ScopeBadge 表达对象或页面数据的归属范围:
- 全局范围显示“全局”,并配合通用范围图标。
- 项目范围显示“项目:项目名称”,不得只显示项目名称。
- 未知或已失效范围显示“范围不可用”,并提供修复入口或只读说明。
- 徽标始终包含文字,不以颜色作为唯一差异。
- 可切换范围时,徽标作为范围选择器的触发器,并提供明确的展开状态和键盘操作。
- 不可切换范围时,徽标为只读状态,不显示下拉箭头。
创建新对象时必须在提交按钮附近再次显示目标范围。跨范围移动属于显式操作,需要说明原范围、目标范围和对关联数据的影响。
6.5 EmptyState
EmptyState 统一包含:
- 能说明状态的图标或简洁插图。
- 一句标题。
- 一至两句原因或下一步说明。
- 最多一个主操作和一个次操作。
必须区分:
| 状态 | 标题示例 | 操作原则 |
|---|---|---|
| 首次为空 | “还没有知识条目” | 提供创建或导入 |
| 筛选无结果 | “没有符合条件的结果” | 提供清除筛选 |
| 搜索无结果 | “未找到相关内容” | 建议修改关键词 |
| 加载失败 | “内容加载失败” | 提供重试并保留错误上下文 |
| 无权限或只读 | “当前范围不可编辑” | 说明原因和可行路径 |
空状态不得使用孤立的短句或仅显示图标。加载中不得先闪现空状态。
6.6 危险操作
共享危险操作样式包含:
danger-ghost:列表行、菜单和工具栏中的删除入口。danger-solid:确认对话框中的最终危险操作。danger-zone:设置页中集中展示的高影响操作区域。
普通页面不得用实心红色按钮与主操作并列。危险入口必须使用具体动词和对象,例如“删除知识条目”,避免只写“确定”。
6.7 数据表格与活动列表
- 表头、单元格、空值、状态和行操作使用统一对齐规则。
- 文本默认左对齐,数值右对齐,状态与短标签可居中。
- 时间显示使用一致格式,并在需要时通过工具提示提供完整时间和时区。
- 行操作默认放在行末。高频安全操作可直接显示,低频或危险操作进入更多菜单。
- 活动记录必须保留操作者、动作、对象、范围、结果和时间等审计语义,不用纯图标代替关键字段。
- 表格密度可以选择“默认”或“紧凑”,但同一页面不得混用。
6.8 应用侧栏
主侧栏用于一级导航、最近会话和稳定的账户入口,必须通过表面、结构线和选中状态建立清楚但不过度装饰的层级。
- 浅色侧栏使用冰蓝灰表面,与白色主内容画布形成明确边界;深色侧栏使用比主画布略亮的蓝灰表面。
- 一级导航与最近会话之间、最近会话与底部账户区之间必须有可见结构分隔线。浅色主题使用
--border-default,深色主题可在可辨前提下使用--border-subtle。 - 当前导航项和当前会话必须同时使用至少三种信号中的两种:强调背景、可见边框、图标或文字强调。浅色主题的当前项优先使用更完整的蓝色选中表面和较高字重。
- 未选中项保持平整,不为每一行添加卡片边框或阴影。悬停反馈不得强于选中状态。
- 账户与设置入口固定在侧栏底部。已有稳定设置入口时,不在顶栏重复提供同一入口。
6.9 应用顶栏与全局操作
应用顶栏用于窗口级状态、侧栏开关和低频全局操作,不承担页面标题或主要导航。顶栏必须保持紧凑,不能与页面内容争夺注意力。
- 顶栏高度默认为
58px,图标按钮使用34px × 34px点击区域。 - Runtime 状态、同步状态等短标签使用
--font-caption,不得放大为正文标题。 - 浅色与深色切换属于持续可用的窗口级操作,直接显示太阳或月亮图标,并通过可访问名称说明将切换到的主题。选择必须持久化,切换不得改变布局。
- 顶栏只直接显示当前任务所需的高频操作。已有侧栏账户设置入口时,不再重复显示 Runtime/设置入口;使用帮助优先放在相关操作附近,而不是为单个帮助项创建“更多”菜单。
- 只有存在至少两个无法由稳定入口承载的低频全局操作时才增加全局菜单,不为了容纳一个冗余入口而显示省略号按钮。
- 窄窗口下优先压缩状态标签并保留图标按钮,不隐藏窗口控制、当前范围或进行中的风险状态。
- 使用全局菜单时,菜单项使用
--font-body、14px图标和约32px单项高度;标签使用短名称。菜单保留menu、menuitem语义,支持上下方向键、Home、End 和 Escape,关闭后焦点返回触发按钮。
6.10 上下文单选菜单
模型、专家角色和工作模式属于同一输入上下文,其选择器必须共享结构、尺寸和菜单视觉,不能出现一个精细菜单与两个风格不一致的原生下拉框。
- 触发按钮复用统一的模型选择按钮样式,保持相同高度、圆角、边框、展开指示和焦点状态。
- 菜单使用
menu与menuitemradio语义,当前项同时显示选中标记和aria-checked。选项可以包含一行简短说明,但标签和说明不得被截断到无法区分。 - 支持上、下方向键、Home、End、Enter 或 Space、Escape;打开后焦点进入当前项,关闭后返回触发按钮。
- 点击或聚焦菜单外部时关闭;同一输入区内的模型、专家和模式菜单互斥展开。
- 不可用选项保持可读并说明原因,键盘导航不得停留在不可选择项上。
- 仅在选项简单且不需要说明、禁用原因或一致菜单行为时使用原生
select。
6.11 应用通知与就地反馈
应用级通知统一进入全局通知视口,页面不得自行复制通知卡片或在内容流中长期堆放短期消息。
- 异步操作成功、无需立即处理的信息,以及不属于某个字段的异步失败,使用应用级
success、info或error通知。 - 成功和信息通知默认在约 4.5 秒后自动消失;错误通知保持可见,直到用户关闭或同一去重键的更新替换它。
- 同一语义和文案的重复通知应去重。通知正文必须有长度上限,不包含凭据、私人内容或未脱敏的提供商响应。
- 字段校验、破坏性确认、操作进度、阻塞整个页面的状态,以及需要就地重试或修正的错误保留在相关控件附近。
- 就地错误必须与对应字段或操作建立程序化关联;全局错误使用
alert和 assertive 实时区域,成功与信息使用status和 polite 实时区域。 - 一个事件只能选择一种主要反馈位置,不得同时显示页内横幅和全局通知。失败时不得因通知切换而清空用户输入、筛选或未提交草稿。
7. 交互状态
所有可交互组件必须实现:
- 默认:文本、边框和背景层级清晰。
- 悬停:提供轻量背景或边框反馈,不改变布局。
- 按下:反馈比悬停更强,持续时间使用
--motion-fast。 - 键盘焦点:显示至少
2px的高对比焦点环,不被容器裁切。 - 选中:同时使用背景、边框、图标或字重中的至少两种信号。
- 禁用:降低强调度,同时保留可读标签,并通过说明或工具提示解释原因。
- 加载:防止重复提交,保留原按钮宽度并显示进行中标签。
- 错误:字段或局部操作错误就近显示可执行说明;非局部异步错误使用不会自动消失的应用级错误通知。
异步提交成功后更新内容并通过统一应用通知提供明确反馈。失败时保留用户输入和筛选上下文。
8. 范围与数据语义
8.1 页面范围
- 页面范围决定当前列表、搜索、创建和批量操作针对的数据集合。
- 页面标题区必须持续显示当前范围。
- 搜索框占位文案应反映范围,例如“搜索当前项目的知识”。
- 切换范围后清理不再有效的选择项,并明确提示数据集合已变化。
8.2 对象范围
- 详情页或主从布局的右侧面板显示所选对象自身的范围。
- 当页面范围与对象范围不一致时,必须显示解释,不得静默混合。
- 全局对象可被项目引用时,应分别表达“归属范围”和“当前引用关系”。
8.3 操作范围
批量操作、导入、删除、移动和自动化运行前,界面必须明确:
- 将影响哪些对象。
- 对象属于全局还是某个项目。
- 操作是否可撤销。
- 是否影响关联任务、知识引用或历史记录。
9. 破坏性操作政策
9.1 风险等级
| 等级 | 示例 | 要求 |
|---|---|---|
| 低 | 移除可立即恢复的筛选、取消未保存草稿 | 通常无需确认,必要时提供撤销 |
| 中 | 删除单个可恢复对象、停止正在运行的任务 | 显式确认或操作后撤销,说明直接影响 |
| 高 | 永久删除、批量删除、清空历史、删除被引用对象 | 必须使用确认对话框,说明范围、数量和不可逆性 |
9.2 确认对话框
- 标题包含具体动作和对象,例如“永久删除 12 条活动记录?”
- 正文说明范围、关联影响和恢复可能性。
- 取消按钮在前,危险按钮在后。初始焦点放在取消按钮。
- 最终按钮使用
danger-solid,标签重复具体动作。 - 仅对高影响且不可恢复的操作要求输入对象名称或确认短语,避免把摩擦用于所有删除。
- 提交期间锁定重复操作。失败后保持对话框打开并显示可处理的错误信息。
9.3 撤销与反馈
- 可恢复删除优先在操作后显示带“撤销”的持久通知。
- 撤销窗口结束前,不把操作描述为“永久删除”。
- 删除成功后更新列表、选中项和计数。主从布局中被删除对象的详情面板应回到明确的未选择状态。
- 审计记录不得因普通对象删除而被静默移除。
10. 深色主题
- 深色主题通过语义令牌替换实现,不在组件中使用主题条件分支选择原始颜色。
- 主画布使用深海军蓝,侧栏、顶栏、输入区和浮层使用逐级提亮的蓝灰表面;表面层级主要依靠亮度和边框区分,避免大面积纯黑与高亮白形成刺眼对比。
- 深色强调色使用明亮但不荧光的蓝色,成功状态使用青绿色。用户消息等大面积强调表面使用更深的实心蓝,确保反白文字舒适可读。
- 输入框、代码块、表格悬停、选中行、弹窗遮罩和滚动条必须分别检查深色值。
- 图片、图表和状态色在深色背景下保持可读。图表系列不能只靠色相区分,还应使用形状、线型或标签。
- 焦点环、危险文本和弱文本在两种主题下都满足对比度要求。
- 原生控件和滚动条声明正确的
color-scheme。 - 主题切换不得导致布局、边框宽度或字号变化。
11. 无障碍
11.1 键盘与焦点
- 所有交互均可通过键盘完成。
- 焦点顺序与视觉顺序一致,打开弹窗后焦点进入弹窗,关闭后返回触发元素。
- 页面导航链接按正常 Tab 顺序操作。同页签组和单选组使用方向键,菜单使用上下方向键和 Escape。
- 不给不可交互容器添加焦点,不用
div模拟按钮而缺少按钮语义。
11.2 语义与标签
- 图标按钮必须有可访问名称,并在视觉上提供工具提示。
- 表单控件有持久标签,不能只使用占位文案。
- 状态变化使用适当的实时区域,但避免对频繁日志逐条播报。
- 错误信息与对应字段建立程序化关联。
- 表格使用正确的表头关系,复杂审计记录在窄屏下仍保持字段标签。
11.3 对比度与触控目标
- 正文与背景对比度至少为
4.5:1,大号文本至少为3:1。 - 控件边界、焦点和关键图形对比度至少为
3:1。 - 常规交互目标建议至少
32px × 32px。紧凑表格可使用28px高度,但相邻目标之间必须有足够间隔。 - 文字缩放至
200%时,核心操作、范围信息和错误提示不能被裁切。
12. 响应式与窗口规则
GoodBuddy 是可调整窗口大小的桌面应用。响应式设计优先保证任务连续性,不简单隐藏信息。
12.1 宽窗口,1200px 及以上
- ���用各
PageShell的完整最大宽度。 dashboard可使用 3 至 4 列卡片。master-detail保持双栏,详情区获得主要空间。
12.2 中等窗口,960px 至 1199px
- 页面左右内边距为
24px。 - 仪表盘降为 2 列。
- 主从布局缩小左栏,但不得低于
280px。 - 表格优先收起低优先级列到详情或行展开区,不隐藏范围、状态和时间。
12.3 窄窗口,720px 至 959px
PageHeader的操作区换行。master-detail变为单面板导航。进入详情后提供明确返回列表的按钮。- 仪表盘使用单列或 2 列,取决于卡片最小宽度。
PageTabs可单行横向滚动,不换成下拉菜单。- 宽表格在自身容器内横向滚动,并固定关键标识列时确保键盘可达。
12.4 极窄窗口,小于 720px
- 页面左右内边距为
16px。 - 标题、范围徽标和操作纵向排列,但范围不得隐藏。
- 主操作可以占满可用宽度,次操作进入更多菜单。
- 分段控件可等分整行,筛选工具栏改为可展开区域。
- 聊天输入区保持可见,并考虑窗口安全边距。
- 对话框使用接近全宽的布局,仍保留
16px外边距。
13. 页面应用规范
13.1 聊天
- 使用
reading壳层,消息流与输入区共享宽度。 - 对话标题和当前项目范围位于
PageHeader或对话上下文区,不在消息流中重复。 - 模式、模型或工具权限属于上下文控制,不与页面导航页签混用。
- 模型、专家角色和工作模式使用统一的上下文单选菜单,并保持菜单互斥、键盘可达和选中状态明确。
- 已选择的工作模式在触发按钮中只显示
Ask或Execute;完整中文含义和说明保留在菜单选项、可访问名称及输入区下方的模式说明中。 - 宽度大于
700px时,添加内容、知识范围、专家、模式和模型控件保持同一行;仅在窄输入区中换行,不能因为允许换行而让所有窗口都固定显示两行。 - 输入框原生支持
Ctrl+V:文本直接进入草稿,图片转换为本次消息附件。文件选择由上传按钮承担,不再提供独立“读取剪贴板”按钮;默认工具栏也不提供“截取当前屏幕”和“选择应用窗口”入口,避免与系统粘贴、文件选择和后续工具执行重复。 - “Enter 发送 · Shift+Enter 换行 · Ctrl+V 粘贴图片或文本”等输入操作提示放在空输入框内部,作为主占位文案的次级行;不得在输入框下方单独占用第二行。输入框下方只保留一行当前模式、安全边界或全局快捷键说明。
- 输入操作提示不能替代表单的可访问名称,输入框始终保留持久的程序化标签。
- 空对话展示可执行的起始建议,发送失败保留输入并提供重试。
13.2 最近对话
- 使用
standard壳层和统一PageHeader。 - 搜索、范围和时间筛选位于筛选工具栏。
- 行项目统一显示标题、范围、最近更新时间和必要状态。
- 删除入口使用
danger-ghost,并按数据可恢复性执行确认或撤销策略。
13.3 知识库
- 使用
master-detail壳层。 - 左侧负责范围、搜索、筛选和条目选择,右侧负责详情、编辑和预览。
- 两侧均只使用语义颜色令牌,禁止内联浅色背景或边框。
- 选中条目后持续显示对象范围。没有选中项与知识库为空必须使用不同状态。
- 窄窗口切换为单面板导航,不把双栏压缩到不可读。
13.4 智能心跳
- 使用
dashboard壳层。 - 顶部先呈现运行状态、当前范围和主操作,再呈现指标和配置。
- 状态卡片使用统一状态令牌,不只依赖颜色。
- 运行历史与配置使用明确区块,不以多套相似页签混合导航、开关和筛选。
13.5 任务与活动
- 任务使用
standard壳层,活动记录使用dashboard壳层。 - “任务 / 活动”作为同级页面时使用
PageTabs。 - 任务状态筛选使用
SegmentedControl或筛选工具栏,不再模拟页签。 - 活动记录保留审计字段和范围,支持独立容器横向滚动。
- 批量停止、删除和清空历史遵循破坏性操作政策。
13.6 魔法笔记
- “笔记 / 待办”属于同一工作台内的同级内容面板,使用
PageTabs的segmented视觉变体,与模型设置的分段控件保持同一外观。 - 页签切换保留
tablist、tab和tabpanel语义;待办状态仍使用独立的SegmentedControl,不得与内容页签合并。 - 创建、保存、更新、删除和 AI 评论完成等短期结果进入应用级通知,不在编辑区或列表上方堆放页内通知。
- 标题或正文校验、删除确认、同步进度和可就地恢复的错误仍靠近对应编辑器或操作呈现。
13.7 设置中心
- 全页设置使用固定标题区、左侧分类导航和独立滚动的内容区。右上角关闭按钮是离开设置中心的稳定入口。
- 全页设置标题区依靠留白与内容区分层,不在标题下方绘制贯穿整个工作区的分隔线;模态设置可以保留标题边界。
- 设置中心不显示全局操作页脚,避免重复关闭入口和没有功能意义的整宽分隔线。
- 所有分类使用共享的
SettingsCategoryHeader呈现分类标题、说明、错误与操作,不得在内容卡片内复制分类标题或创建页面专属操作栏。左侧分类名称与说明来自同一份分类定义,新增分类时不得分别维护导航和内容标题。 - 当前分类存在“保存”或“测试”等未提交配置操作时,统一放在分类页头右侧;主保存操作在最右侧,测试等次操作排列在其左侧。
- 自动生效、仅执行即时命令或自行管理编辑流程的分类不显示全局保存操作。窄窗口下操作区可以换行,但保存入口必须保持清晰可见。
- 保存或测试成功统一进入应用通知视口,并按全局规则自动消失,不在分类页头或内容卡片中保留持久成功文案。加载、保存和测试错误显示在分类页头下方,并保留可处理的上下文。
13.8 文档解析设置
- 设置中心新增独立的“文档解析”分类,统一管理聊天附件、知识库导入以及后续文档审阅场景使用的提取、转换和 OCR 策略。OCR 不作为普通对话模型出现在“模型连接”中。
- 分类页头说明文档解析的跨场景作用,右侧依次显示“测试解析”和“保存设置”;保存位于最右侧。测试必须选择真实文件并执行实际解析,不能只检查模型文件或接口连通性。
- 页面首先显示原生解析、文档转换和 OCR 的运行状态,并明确当前可处理格式、回退能力与不可用原因。部分能力未配置时使用“部分可用”状态,不得把原生文本解析一并标记为失败。
- “使用场景”分别配置聊天附件和知识库导入。普通用户选择“自动解析”“快速文本”“完整索引”等预设;阈值、并发和超时放入默认折叠的高级设置。
- 本地 OCR 的全平台基线使用同一组 PP-OCRv6 ONNX 模型和 ONNX Runtime WebAssembly,在 Windows、macOS、Linux 的 x64 与 arm64 上保持相同功能。原生 ONNX、WebGPU、DirectML、CoreML 或 CUDA 只能作为可选加速,失败时必须回退到 WASM CPU。
- OCR 模型管理与语音模型保持一致:应用不内置权重,用户可按需从 ModelScope 下载,也可在联网设备导出 ZIP 并在离线或内网设备直接导入。语音和 OCR 模型的下载、取消、ZIP 导入、ZIP 导出、删除与打开受管目录使用同一交互语义;ZIP 操作不得隐式切换当前模型或保存解析设置。
- OCR 模型卡片必须持续显示来源、语言、运行时、体积、安装状态和许可。“打开 ModelScope”直接位于卡片右上角,不再使用“模型详情与手动导入”折叠区。窄窗口下仓库操作换行到模型摘要下方,仍须保持可访问名称和键盘操作。
- PP-OCRv6 提供三个已实现档位:Tiny 约 6 MiB,适合低资源设备;Small 约 30 MiB,官方支持 50 种语言并作为推荐档位;Medium 约 132 MiB,官方支持 50 种语言、质量更高但速度较慢,界面必须提示其更高的内存占用和延迟。
- 本地模型按受管目录和固定清单加载。ModelScope 下载地址必须固定不可变 revision、字节数和 SHA-256;下载先进入临时目录,全部校验成功后再原子安装。识别时不得从网络或可变分支临时加载模型。
- 模型 ZIP 使用版本化的
goodbuddy-model.json清单,声明模型类型、内置目录 ID、文件角色、大小与 SHA-256。导出前重新校验已安装文件;导入时限制压缩包大小、条目数、单文件和总展开大小,拒绝路径穿越、重复、未知、缺失或嵌套条目,并以应用内置目录重新校验后原子安装。ZIP 内的自声明信息不能扩大受信任模型集合。 - PDF 先读取文本层。仅当页面无有效文本、乱码比例过高或用户选择“始终 OCR”时渲染该页并识别;不得因为单页需要 OCR 而丢弃其他页面已经提取的可靠文本。
- DOCX、XLSX、PPTX 优先保留段落、单元格、公式、备注等原生语义。转换为 PDF 用于补充版面、页码、图表和图片理解,不作为唯一中间格式。
- DOC、XLS、PPT 等旧格式通过受控转换 Provider 生成新式 Office 文档和 PDF。转换子进程必须禁用宏和网络,限制输入、输出、内存、超时与临时目录,并在关闭或取消时清理。
- OCR 来源使用“本地模型 / 远程服务”互斥选择。选择本地后显示模型下载、模型下拉选择和本地运行参数;选择远程后显示 MinerU、PaddleOCR-VL 等服务连接配置。未实现的远程服务入口保持可读但禁用,不再增加与来源选择重复的“隐私与云端处理”授权区。
- 用户配置并保存远程 OCR 服务即表示选择该处理路径,不再逐场景重复询问。界面仍须明确显示当前服务名称、处理范围和远程属性,API 密钥只保存在主进程加密设置中,未选中远程服务时不得上传文档。
- 解析结果使用统一文档结构,至少保留文档标题、来源格式、页码或工作表定位、正文块、置信度、处理方式和警告。聊天附件对结果做有界截断,知识库使用完整结果分块和索引。
- 测试结果显示文件类型、页数、实际工作流、提取字数、OCR 页数、耗时和警告。测试文件不得自动进入聊天上下文或知识库。
14. 文案规则
- 使用简体中文,动词直接、对象明确。
- 页面标题使用名词,例如“知识库”“智能心跳”“活动记录”。
- 按钮使用“动词 + 对象”,例如“新建任务”“导入知识”“停止运行”。
- 状态文案描述事实,例如“正在同步”“上次运行失败”,不使用含糊的“异常”。
- 错误提示包含发生了什么、用户可以做什么。保留必要的错误上下文,但不得暴露凭据、授权头、私人文档或未脱敏的提供商响应。
- 同一概念固定使用一个名称,不交替使用“项目空间”“工作区”“范围”等近义词。产品内统一使用“范围”表达全局与项目归属。
15. 迁移检查清单
15.1 基础层
- 建立浅色与深色语义颜色令牌,移除业务组件中的原始颜色值。
- 建立白色浅色主画布、冰蓝灰侧栏与深海军蓝深色表面的稳定层级。
- 建立间距、字体、圆角、阴影、层级和动效令牌。
- 为主题切换、减少动态效果和原生控件设置全局规则。
- 建立组件交互状态和焦点环基线。
- 验证浅色侧栏结构分隔线与导航、会话选中状态清晰可辨。
15.2 页面壳层与层级
- 实现
PageShell的reading、standard、dashboard、master-detail变体。 - 按页面映射替换
820px、900px、1040px和全宽等分散宽度声明。 - 每个一级页面只保留一个
PageHeader和一个一级标题。 - 移除内容卡片中与页面标题重复的标题。
15.3 共享组件
- 实现并迁移
PageHeader。 - 使用
PageTabs统一同级页面导航。 - 使用
SegmentedControl统一少量互斥视图和状态切换。 - 需要分段外观的同级面板使用
PageTabs的共享segmented变体,不复制控件样式。 - 建立统一筛选工具栏,移除以页签样式伪装的筛选。
- 将短期成功、信息和非局部异步错误接入应用通知视口,移除页面专属通知横幅。
- 实现
ScopeBadge并覆盖全局、项目、失效和可切换状态。 - 实现
EmptyState的首次为空、无结果、失败和只读变体。 - 实现
danger-ghost、danger-solid和danger-zone。 - 统一模型、专家角色和工作模式的单选菜单结构、视觉与键盘行为。
15.4 页面迁移
- 聊天迁移到
reading,统一消息流与输入区宽度。 - 将输入快捷键与附件提示置于空输入框内部,输入区下方保持单行说明。
- 最近对话迁移到
standard,统一搜索、范围、时间和删除行为。 - 知识库迁移到
master-detail,清除内联浅色样式并补齐窄窗口单面板流程。 - 智能心跳迁移到
dashboard,统一状态卡片、配置和运行历史层级。 - 任务迁移到
standard,活动记录迁移到dashboard,统一导航、筛选和表格行为。 - 设置中心使用共享分类定义与
SettingsCategoryHeader,将保存与测试操作统一放到分类页头右侧,并把成功反馈接入应用通知。 - 文档解析设置统一聊天附件与知识库的解析预设、OCR 状态、转换状态、隐私限制和真实文件测试。
15.5 验收
- 在浅色与深色主题下检查所有页面、弹窗、菜单、输入框、表格和空状态。
- 在大于等于
1200px、960px、720px和小于720px的窗口宽度检查布局。 - 仅使用键盘完成导航、筛选、创建、编辑、确认和取消。
- 验证焦点恢复、可访问名称、表单错误关联和实时状态播报。
- 验证页面范围、对象范围和操作范围在关键流程中始终可见。
- 验证删除、批量操作、停止运行和清空历史符合风险等级策略。
- 验证加载中、首次为空、筛选无结果、搜索无结果、失败和只读状态不会互相混用。
- 在 Windows、macOS、Linux 的 x64 与 arm64 上执行真实本地 OCR,并验证 WASM CPU 回退、取消、超时和离线运行。
- 在联网设备导出语音与 OCR 模型 ZIP,在离线设备导入后执行真实推理;验证错误模型 ID、篡改文件、路径穿越、未知条目和压缩炸弹均被拒绝。
16. 完成标准
一个页面只有在满足以下条件时才视为完成迁移:
- 使用明确的
PageShell变体,没有页面专属整体宽度。 - 使用统一标题层级、共享导航和筛选控件。
- 所有颜色、间距、字体、圆角和阴影来自令牌。
- 全局或项目范围在浏览、创建、编辑和危险操作中均可见。
- 浅色、深色、键盘和各窗口宽度下均可完成核心任务。
- 空状态、错误状态和危险操作符合本文规则。