跳转到正文

一次以减法为主的博客改造:时间线、去装饰与中文排版

这一轮改造的主线是减法。做完之后统计了一下:新增 4 个组件和 2 条分页路由,删除 16 个源码文件、整个 docs/ 目录和 6 项功能。页面上留下来的东西更少,但每一样都有明确的存在理由。

下面按主题记录,重点是每个决定背后的依据,而不是改了哪几行。

一、三个列表页统一为时间线

改造前,三个列表页各说各话:

  • 首页:文章卡片和短文块混排,标题在左、日期在右
  • 文章列表:按年份分组的紧凑单行,日期是 07-07
  • 短文列表:左边框 + 右侧日期

同一个站点里三套视觉语言,从首页点进文章列表,眼睛要重新适应一次。

现在统一成一条竖线加圆点的时间线:文章是实心点,短文是空心点,日期一律 2026-07-07 18:33:32 周二,左对齐。首页因为混排,圆点后面额外带一个「文章 / 短文」标签;另外两个页面整页同类,不需要标签。

为了保证三处渲染完全一致,抽了四个组件:

组件职责
Timeline.astro时间线容器,左边框即竖线
TimelineItem.astro单条:圆点 + 时间 + 可选类型标签,正文走 slot
PostTimelineItem.astro文章条目,首页和文章列表共用
TimelineStats.astro页尾统计

圆点和竖线的对齐是这里唯一有技术含量的地方。圆点绝对定位,左移量等于容器内边距 + 边框宽度的一半 + 圆点半径,也就是 start-[calc(-1.5rem-5px)]。这个值和容器的 ps-6 是配套的,改一个必须改另一个,所以在两个组件里都写了注释说明这层耦合。

二、文章和短文都加了分页

两个列表页原来都是一次性输出全部内容。现在改成 Astro 的 [...page] 分页路由,URL 保持不变:第一页仍是 /posts/notes,之后是 /posts/2/notes/2

分页大小拆成了两套配置,因为短文比文章短得多,密度不该一样:

posts: { perPage: 4, perIndex: 4 },
notes: { perPage: 10, perIndex: 4 },

需要注意的是 /posts/[...page] 和已有的文章详情路由 /posts/[...slug] 在同一层。构建时验证过:两者各自生成自己的路径集合,不冲突,也没有警告。

页尾统计的位置是特意选的。原来每个年份分组上方有一个「2026 · 4 篇」的标题,从首页点「全部文章」进来,第一眼是个大号年份,节奏被打断。现在年份分组整个去掉——条目本身已经带完整年份,再来个标题是重复信息——统计挪到列表末尾,也就是分页所在的位置,显示为「共 4 篇 · 2026 4 篇」。统计的是全站总数,不是当前页。

三、删掉的六项功能

功能删除理由
标签系统4 篇文章 6 个标签,其中「折腾」覆盖 100%(零区分度),cssfont 各只有 1 篇(死胡同)。个人博客不是知识库
返回按钮浏览器返回能恢复列表滚动位置,它只能跳到列表顶部,更差
回到顶部同上,功能与浏览器/手势重复
阅读进度条长文里持续存在的视觉噪音
编辑页面链接个人博客没有协作者,这个入口面向的是不存在的用户
上一篇 / 下一篇时间上相邻的两篇文章通常没有内容关联

删除时的连带清理比功能本身多。以标签为例,除了两个路由页和 Tag.astro,还牵出:Breadcrumb.astro(只有标签页在用,成了死代码)、getUniqueTags.tsslugify.ts 里的 slugifyAll、i18n 的四条文案、文章 schema 的 tags 字段。返回按钮牵出的更远——Main.astrodata-backUrl、首页的 data-home-path、搜索页记录 backUrl 的三处代码。

顺带发现两个组件在之前的改动中已经没人引用:Card.astro(首页改时间线、标签页删除后失去全部调用方)和几个只服务于已删功能的图标。

页面上的装饰线也一并去掉了:页头下方、页尾上方、文末分隔线、列表页统计上方。去掉线之后页尾需要补偿,做法不是把线加回来,而是降级 + 拉开留白——页脚整体改成 text-muted-foreground text-sm,上方留白从 24px 提到 48px。用层级替代分隔线,这是去线设计能成立的前提。

四、目录改成横线式

桌面端的文章目录原来是一个展开的标题列表,长期占着右侧一块。现在默认只显示长短横线:h2 是 16px 的线,h3 是 8px。

  • 读到哪一节,哪条线点亮(沿用原有的 IntersectionObserver
  • 鼠标移上去才展开标题,容器是 w-fit,收起时只有横线那么宽,不会大片区域误触
  • 一个图钉按钮可以把展开状态固定住,存在 localStorage

横线长短不同会让标题起始位置参差,所以给横线套了一层固定宽度的容器,长短只体现在线本身,标题一律从同一个位置开始。

移动端保持原来的内联折叠目录——横线式目录需要正文两侧的留白,窄屏没有。

五、配色:从冷白蓝到暖纸墨绿

先测了原配色的对比度,发现两个实际缺陷:

  1. 深色模式的边框是橙褐色 #ab4b08。这在页头页尾还只是两条线时无所谓,但时间线的竖线用的正是这个变量——深色下一条棕橙色的线贯穿全页,和橙色圆点同色系,圆点的标记作用被抵消了。
  2. 深色模式下强调色上的白字只有 2.86:1,不满足 AA。它用在文本选中的样式上,选中时几乎看不清。

修完这两个之后,重新考虑了整套色板。原来的浅色背景是 #fdfdfd,亮度 98.2%,接近纯白。这对中文衬线是最不友好的组合:宋体系横画极细,在高亮度纯白背景上细笔画会产生光晕,长文读十分钟就累。

新色板:

变量浅色深色
--background#faf8f4 暖纸#1f1e1c 暖黑
--foreground#2c2a26#e8e4dc
--accent#2f6b5f 墨绿#7fbfae
--muted-foreground#5f5a52#a9a49a
--border#dbd3c6#423d35

对比度:正文 13.50 / 13.14,强调色 5.84 / 7.90,次要文字 6.45 / 6.71。全部远超 AA 4.5:1。改造前浅色的次要文字只有 4.75,卡在及格线上,而它承担着日期、页脚、统计等全部次要信息,且都是小字。

代码块的深色主题也跟着从 night-owl 换成了 min-dark。前者是深蓝底 #011627,配暖黑页面会是一块蓝色孤岛;后者底色 #1f1f1f,和页面几乎同级,且与已在使用的 min-light 是同一套设计。

强调色的用量比色相更重要。 墨绿定下来之后发现整页还是偏彩,原因是 accent 同时充当文章标题色、列表符号色、引用条颜色——标题是页面上字号最大、字重最重的元素,把它染成强调色,强调色就不再是强调色而是主色。现在标题改回正文色、悬停才变绿,列表符号降为弱灰。墨绿只剩下时间线圆点、目录高亮、导航当前项和交互反馈。

六、中文排版

从构建产物的 CSS 里读到三个硬数据,都不符合中文长文阅读:

  1. .app-prose 没有设置 line-height,正文继承的是 Tailwind preflight 的 1.5
  2. 段落间距 0.8em = 12.8px,不到半行
  3. 正文 16px,容器 768px,每行约 48 个汉字

对应的修改:

  • 行高 1.5 → 1.8。汉字是全角、笔画密,行距不够时上下行会互相干扰。中文正文的通行区间是 1.7–2.0。
  • 段距 0.8em → 1.4em。原来段落之间几乎粘连,只能靠语义断句。
  • 字号 16px → 17px / 18pxsm 断点)。中文在同 px 下比西文视觉更小,因为西文有大量空白字腔,汉字是密排方块。这同时解决了行长问题:18px 时每行约 43 字,落回中文舒适区(30–45 字)。

还修了三处从模板继承来的西文假设:

  • blockquote 的斜体。中文没有真正的意大利体,浏览器只能做合成倾斜,把字形整体切变,笔画粗细和字面结构都会失真。同样的问题之前还出现在 h3 上。
  • 行内代码的上下内边距。原来是 p-1,四周都有 4px,一段话里出现几个行内代码,行距就会参差。改成只留左右内边距,并加了 0.15em 的外边距,中英混排时不至于贴着汉字。
  • 表格字号prose 默认压到 0.875em,中文在表格里本来就挤。

最后理了一遍字号阶梯。提高正文字号有个副作用:h2 用的是 em 相对单位,跟着从 24px 涨到 27px,而 h1 是固定的 30px——两者只差 3px,章节标题几乎和文章标题一样大,层级塌了。重新排成 ~1.2 倍的比例:

层级字号
文章标题 h130px
正文 h224.3px
正文 h320.7px
正文 h4 / 正文18px
日期、页脚14px

阅读态的字号收归到 .app-prose 一处定义。这个类正好只用在四个需要逐字阅读的地方:文章正文、关于页、首页和短文页的短文正文。定在这里,四处一次同步,新增页面挂上就自动一致。

一点体会

这一轮里,改动最大的几个决定都不是「加个什么功能」,而是「这个东西为什么还在」。标签、返回按钮、回到顶部、进度条——它们都是模板自带的,看起来都很合理,但放到「4 篇文章的个人博客」这个具体语境里,没有一个站得住。

另一个反复出现的模式是:问题往往不在被抱怨的那个属性上。觉得橙色太重,其实是强调色面积太大;觉得文章标题比站名大不协调,其实是 h1 和 h2 只差 3px;觉得页尾少了线不踏实,其实是页尾文字没有降级。换颜色、改字号、加回横线都是治标。