基础
桌面端密度
让桌面端屏幕(768px 起、用鼠标或触控板)紧凑而平静的八条规则:每条规则为什么成立,以及由哪个 token 或部件来保证。
在 768px 起、用鼠标或触控板的屏幕上,即 (width >= 48rem) and (pointer: fine),Raft 画出比手机更紧凑的界面:人们从更远处、用更精确的指针操作。这些规则来自桌面端密度工作的设计评审(stdrc,2026 年 11 月)。每条规则说明要做什么、为什么,以及由什么来保证,所以新屏幕读 token 就能遵守,而不是照抄数字。手机和触屏保持它们自己的尺寸(间距与尺寸)。
规则
1. 能按的单行,只用一个尺寸
侧栏行、菜单和右键菜单的选项、字段、选择框、按钮、标签页、选中的分段、筛选选择器、作为按钮的标签,以及浮动工具栏的按钮,都是 34px 高:控件高度。并排放在一行里的东西高度完全相同。
- 为什么: 并排的两个可按元素差一两个像素,整行就显得粗糙,眼睛还会把更高的那个读成更重要。
- 由什么保证:
control-height(34px)。row-height和option-height读它;md尺寸的 Button、Tabs、SegmentedControl、ToggleGroup、PickerTriggerButton、FilterChip 和浮动工具栏用md:pointer-fine:读它。 - 有意的例外:
- 头部自己的按钮是栏按钮,28px,圆角
bar-button-radius(bar-button-size),放在它们中间的东西也一样(AvatarGroupButton、关注者按钮):头部的操作要比标题轻。 - 嵌在字段里的控件(清除按钮、标签)是
control-embedded-size(22px),离字段边缘 6px。 - 分区标题旁的排序和新建控件是 24px 的标签控件,配 12px 的标题,点击目标 28px。
- 行动号召按钮是
control-height-cta(40px)。
- 头部自己的按钮是栏按钮,28px,圆角
2. 头部是一行,44px
每个头部(面板、侧栏、话题、抽屉、对话框的顶栏、侧边分区)都是一行:标题,然后是同一基线上的辅助信息。它的高度是控件高度加上下的头部留白:34 + 2 × 5 = 44。
- 为什么: 两行的头部让每一栏的接缝高度不同,还把内容往下推。
- 由什么保证:
header-height(control-height+ 2 ×header-air);PanelHeaderContent把标题和PanelMeta排在同一基线上。
3. 外层的东西站得更靠外
分区的标题、分组标签和容器的边缘,都比它们包住的内容更靠外,绝不更靠里,也绝不比内容更空。
- 为什么: 向外缩进的标题读起来是它下面内容的框架;缩进相同时,它读起来只是又一行。
- 由什么保证: 面板的分区标题和设置卡片比它们包含的内容更靠外。
- 在侧栏里(stdrc,2026-11-05,方案 B):两条轴。行的图形(图标、
#、头像)从图形轴开始,离侧栏边缘 16px;行的文字从文字轴开始,40px。分区或分组标题从图形轴开始,比行的文字更靠外,没有高亮,约 24px 高。分区的展开箭头是它的最后一个控件,在标题行的末端,一直显示。行尾的数量和标题行的控件结束在离右边缘 16px 处;行的形状离两侧边缘 8px,内容在形状内 8px。标题行上方 16px、下方 4px;行与行相隔 2px;空分区的提示从文字轴开始(--sidebar-glyph-axis、--sidebar-text-axis)。
4. 间距说明什么属于一起
组内的间距小于组与组之间的间距,两者又都小于容器的内边距。
- 为什么: 人把靠近读成属于一起。设置项控件下面的空白和到下一个设置项的空白一样大时,这个设置项就散了。
- 由什么保证: 组内用
field-gap,分区之间用section-gap,外围用page-inset(16px),它是头部、工具栏、行、分区、抽屉和对话框共用的内容边缘;从头部接缝到下面第一项用page-top(12px)。属于头部下面内容的单独控件(分段控件,规则 7)上方是内容的 12px 顶部内边距,下方 8px,所以它和内容读成一个整体(SegmentedControl)。堆叠设置项的设置卡片内边距 20px,设置项之间 16px,标题到说明 4px,说明到控件 8px(4 和 8 < 16 < 20)。
5. 不给不存在的东西留位置
不要为通常不在的东西保留空白:空闲的“已保存”一行、一列已读回执、一个空槽位。
- 为什么: 预留的空白读起来像有人忘了填的缺口,而且每一行都要为大多数行没有的元素付出空间。
- 由什么保证: 设置卡片里最后一行结果在空闲时不占空间,出现时画在控件下方的空白里,所以什么都不会移动。
6. 按视觉中心对齐
同一行里,不同字号的文字共用一条基线;文字旁的图标、图块或头像以文字的大写字母高度为中心,而不是以行盒为中心;· 这样的分隔符是文字里的字形,所以落在 x 高度上。
- 为什么: 两种字号按盒子居中时,看起来像要从这一行滑下去。
- 由什么保证:
PanelHeaderContent里的items-baseline;头部图块的中心离标题大写字母高度的中点不超过 0.5px。
7. 分隔线分开的是区域,不是控件和它控制的内容
控件属于它控制的内容。分段控件或单独的筛选器放在页面背景上,内容紧接在它下面:不给它一条上下都有线的专属栏。
- 为什么: 开关和它切换的内容之间的一条线把两者切开,还多出一条什么都不承载的界面带。
- 由什么保证: 只放一个分段控件的行不画接缝,它的间距把它和下面的内容连在一起(规则 4)(SegmentedControl);有几个工具的工具栏保留接缝。
8. 从起点开始;身份不变形
默认对齐到行的起点。只有在有意和其他工具编组时,才把控件放到末端。在一个选择里(分段控件、标签页、单选组、排序或筛选菜单),默认选项排在第一个(stdrc,2026-11-05)。头像在每个尺寸都保持贴纸形状:身份不改变形态。