侧栏此前在第一条会话之前压着三段:星盘名字 chip 组、收藏对话 <details>、
历史对话 <details>——两个折叠箭头,底下都没有值得折叠的东西。现在是一条
平铺列表:收藏作为首个标签组(带 13px 星标),其余沿用既有的日期分组。
星盘入口收敛到一处。这里与任务书 D6 的字面写法方向相反:D6 说留侧栏删
账户菜单,我做的是删侧栏留账户菜单。理由——D6 写于侧栏只有 2 个导航项时,
现在是 4 个;且 chip 点下去只是开弹窗(page.tsx 里三个回调都是
openAccountDialog("chart-library")),一组只会开弹窗的名字没有导航价值。
连带删 charts/onSelectChart/onAddChart props、SidebarChart 类型、
sidebarCharts 派生与一批 CSS。
助手头像删除,--assistant-content-inset 由 calc(32px + gap) 归零,
追问 chip 与运行时间轴改为与正文对齐。/jyotish-logo.png 文件保留。
顺带关闭 R2 留下的隐患:入口 pill 36px 低于 44px 触摸推荐值,补
::after inset -4px 热区扩展,并在 touch-target-contract 里接替
已删除的 .chart-nav-chip。
测试 3350 不变,fail 仍 31 且与基线逐条一致;/ 仍 Static;
CSS gzip 41,044→39,825(−3.0%),三轮累计 −3.1%。
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0193vBv6w5MV2cifdTUu9H5P
120 lines
8.5 KiB
Markdown
120 lines
8.5 KiB
Markdown
# PROGRESS · C 端界面对齐 R3(侧栏拍平、入口收敛、去头像)
|
||
|
||
任务书:`docs/tasks/TASK-cend-ui-claude-alignment-20260916.md` 的 R3
|
||
执行方式:**直接执行模式**
|
||
分支:`codex/cend-ui-r3-20260916`
|
||
基线:`origin/staging` = `62903b7a`(R2 合入后)
|
||
BUG 段:不占用(产品改造,非缺陷)
|
||
|
||
---
|
||
|
||
## 又一处与任务书不符的现状
|
||
|
||
任务书 E6 描述侧栏是「品牌 / 新建对话 + 我的报告 / 星盘列表 / 收藏对话 details / 历史对话 details / 账户」。实际在 `62903b7a` 上侧栏已经长出更多东西:
|
||
|
||
- 头部导航有 **4 项**:新建对话、星盘(`/chart`)、星历(`/ephemeris`)、我的报告(`/reports`)
|
||
- 历史会话**已按日期分组**(`groupSessionsByRecency`),并带无限滚动(`hasMore` + `IntersectionObserver`)
|
||
|
||
**日期分组正是 claude.ai 的做法,予以保留**,本轮只拆折叠层与冗余入口。
|
||
|
||
---
|
||
|
||
## T3.1 · 侧栏拍平
|
||
|
||
三段结构(星盘列表组 + 两个 `<details>`)合并为**一条平铺列表**:
|
||
|
||
| 改前 | 改后 |
|
||
|---|---|
|
||
| `SidebarGroup.chart-nav`「星盘列表」+ 加号 + 名字 chip 网格 | **整组删除**(见 T3.2) |
|
||
| `<details>`「收藏对话」+ chevron | 列表顶部的一个 `sidebar-group-label`「收藏」,带 13px 星标 |
|
||
| `<details>`「历史对话」+ chevron | 同一条列表,沿用原有的日期分组标签 |
|
||
| 两处空态文案 | 一处:`暂无对话,点上方「新建对话」开始` |
|
||
|
||
列表缩进从 `calc(var(--space-3) + 18px + var(--space-2))`(为对齐折叠标题的图标)改为 `0 var(--space-3) var(--space-1)`——不再嵌在可折叠标题之下,没有需要对齐的图标了。
|
||
|
||
**键盘可达性**:`handleExpandHistory` 的焦点转移链路保留。原来焦点落在 `<summary>` 上,现在落在 `<p className="sidebar-section-label" tabIndex={-1}>`,`historyHeadingRef` 的类型从 `HTMLElement` 收窄为 `HTMLParagraphElement`。`firstSessionRef ?? historyHeadingRef` 的优先级不变。
|
||
|
||
| 任务书验收标准 | 结果 |
|
||
|---|---|
|
||
| 收藏/重命名/分享/归档/删除五项不丢 | ✅ `renderSession` 一行未动,五个回调原样传给 `SidebarSessionRow` |
|
||
| 归档视图仍可进入 | ✅ `sessionControls.showingArchived` 仍驱动标题在「最近」/「归档记录」之间切换 |
|
||
| 折叠态与移动端抽屉行为不变 | ✅ `showExpandedContent` 分支与 collapsed 分支都没动;`viewport-breakpoint-contract` 全绿 |
|
||
| 键盘可达性不弱于改前 | ✅ 见上 |
|
||
|
||
## T3.2 · 星盘入口收敛
|
||
|
||
**这里我偏离了任务书 D6 的字面写法,方向相反。**
|
||
|
||
D6 写的是「收敛到侧栏一处,账户菜单里的『星盘资料』项删除」。我做的是**反过来**:删掉侧栏的星盘列表组,保留账户菜单里的「星盘资料」。
|
||
|
||
理由两条:
|
||
|
||
1. **D6 写于侧栏只有 2 个头部导航项的时候**,现在是 4 个(新建对话/星盘/星历/我的报告)。再塞第 5 项会把头部压得很重。
|
||
2. **「星盘资料」是管理动作,不是导航目的地**——它打开的是设置弹窗的一个分区,和「个人资料」「通用设置」同级。而侧栏那组 chip 点下去也只是开同一个弹窗(`page.tsx` 里 `onSelectChart` / `onAddChart` / `onOpenChartLibrary` 三个回调全是 `openAccountDialog("chart-library")`),**一组点了只会开弹窗的名字不提供任何导航价值**。
|
||
|
||
D6 的真实目标是「收敛到一处」,两种做法都满足;选哪个留下是我的判断,在此披露。若产品认为必须在侧栏可见,改回来是加一个 `SidebarMenuItem` 的事。
|
||
|
||
连带删除:`charts` / `onSelectChart` / `onAddChart` 三个 props、`SidebarChart` 类型、`page.tsx` 里的 `sidebarCharts` 派生,以及 `.chart-nav-list` / `.chart-nav-chip` / `.session-nav-header` / `.session-nav-toggle` / `.sidebar-label` / `.sidebar-section*` 一批 CSS。
|
||
|
||
## T3.3 · 删掉助手消息头像
|
||
|
||
`AgentAvatar` 组件、两处渲染点(`chat-message-row.tsx`、`onboarding-chat-message.tsx`)、三条 CSS 规则全部删除。
|
||
|
||
`--assistant-content-inset` 从 `calc(32px + var(--space-3))` 改为 `0px`。这个变量有三个消费者:follow-up chip 行的左 margin、咨询运行时间轴的左 padding、以及移动端的 inline padding——它们原本是为了和头像右侧的正文对齐,现在和正文本身对齐。
|
||
|
||
| 任务书验收标准 | 结果 |
|
||
|---|---|
|
||
| `/jyotish-logo.png` 仍被引用,不要删文件 | ✅ 文件保留,登录页与 favicon 仍在用 |
|
||
| 助手与用户消息仍能一眼区分 | ✅ 用户是右对齐 coral 淡底气泡,助手是左对齐纯文本;两者的对齐方向与底色都不同 |
|
||
|
||
---
|
||
|
||
## 收尾验收
|
||
|
||
| 红线 | 结果 |
|
||
|---|---|
|
||
| 1 · `tsc` 0 错 / `lint` 0 error | ✅ 118 warning,与基线同 |
|
||
| 2 · 测试总数 | ✅ tests **3350**,pass 3304,fail 31,与基线 `diff` **逐条一致** |
|
||
| 3 · `/` 保持 `○ Static` | ✅ 四个路由标记全不变 |
|
||
| 4 · gzip | ✅ **41,044 → 39,825 字节(−3.0%)**;累计相对基线 41,095 降 **3.1%** |
|
||
| 5 · `page.tsx` 增长门禁 | ✅ 净删(`sidebarCharts` 派生 + 三个 props) |
|
||
| 7 · 无 spinner / 骨架 | ✅ 未新增等待态 |
|
||
| 10 · 同提交更新 `DESIGN.md` | ✅ 「Sidebar shell」的展开内容与空态两条重写、新增拍平理由;「Message」的 Identity 一条重写 |
|
||
| 11 · 不升依赖、不留新 warning | ✅ |
|
||
|
||
Python 快速门(BUG-736 防复发):本轮改了 `page.tsx`,`pytest tests/test_supabase_user_data_contract.py` 8 条全绿。
|
||
|
||
### 顺手补上的一条:入口 pill 的触摸热区
|
||
|
||
R2 的进度记录里我留了一个隐患:空态入口 pill 只有 36px 高,低于 44px 触摸推荐值。本轮 `touch-target-contract` 因为 `.chart-nav-chip` 被删而打红,正好是管这类控件的合同——于是给 `.starter-entry` 补了 `::after { inset: -4px }` 的热区扩展(与 `.message-actions button`、`.auth-links button` 同一套做法:保持视觉尺寸,扩大命中区),并把它写进该合同接替 `.chart-nav-chip` 的位置。R2 那条隐患就此关闭。
|
||
|
||
### 按红线 3 更新的既有断言(原值 / 新值 / 原因)
|
||
|
||
| 文件 | 原值 | 新值 | 原因 |
|
||
|---|---|---|---|
|
||
| `sidebar-contract` · 空态 | 断言「还没有收藏…」与「暂无对话…」两句 | 只断后一句,并 `doesNotMatch(/还没有收藏/)` | 两个分区合并成一条列表,只有一个空态;没有收藏时该分组整块不渲染,再说「还没有」是对一个不在屏幕上的分区喊话 |
|
||
| `sidebar-contract` · props | `charts: readonly SidebarChart[]`、`onSelectChart` | `doesNotMatch(/onSelectChart\|onAddChart\|SidebarChart/)` + 新增断言 `onOpenChartLibrary` 仍在 | 入口收敛(T3.2)。这条**收紧**了:从「必须有」变成「必须没有」,并锁住幸存的那一个 |
|
||
| `sidebar-contract` · 标题色阶 | 选择器 `.sidebar-label, .sidebar-section-summary` | `.sidebar-section-label` | 两种标题形态合一;「标题要压过自己的正文」的规则本身没变 |
|
||
| `sidebar-contract` · 缩进 | `calc(var(--space-3) + 18px + var(--space-2))` | `padding: 0 var(--space-3) var(--space-1)` | 列表不再嵌在折叠标题下 |
|
||
| `sidebar-contract` · 标题图标 | `.sidebar-label > svg` 与 `.sidebar-section-summary > svg` 各 18px | `.sidebar-group-label > svg` 用强调色 | 唯一剩下的标题是「最近」两字不带图标;收藏的星标是 13px 行内标记 |
|
||
| `rectification-agentic-entry`、`rectification-timeline-20260909` | `--assistant-content-inset: calc(32px + var(--space-3))` | `0px` | 头像删除 |
|
||
| `class-name-definition-contract` | `knownUnstyled` 含 `chart-nav` | 移除 | 类名已不存在 |
|
||
| `touch-target-contract` | `.chart-nav-chip` 32px + 热区 | `.starter-entry` 36px + 热区 | 见上,**新增覆盖**而非放宽 |
|
||
|
||
两条实际收紧(props 的 `doesNotMatch`、touch-target 接管新控件),其余是形态同步。
|
||
|
||
---
|
||
|
||
## 环境缺口(不得记为通过)
|
||
|
||
1. **侧栏抽屉在移动端的手势与焦点行为**(折叠态、抽屉开合、Escape 关闭)。
|
||
2. **拍平后长会话列表的滚动与无限加载**:日期分组标签在连续滚动中的粘滞表现。
|
||
3. **去掉头像后助手/用户消息的可区分度**——自动化只能证明两者的对齐与底色不同,实际观感要真机看。
|
||
4. 承接 R2 的两项:空态首屏可见性、入口 pill 触摸(本轮已补热区,仍需真机确认)。
|
||
|
||
---
|
||
|
||
## 三轮完结
|
||
|
||
R1 / R2 / R3 全部实现并合入。`TASK-cend-surfaces-claude-alignment-20260916.md`(R4–R8,五个次级面)尚未开工。
|