用 Canvas 画一个正十二边内嵌齿轮花样表盘,这事儿我前后折腾了三个晚上。第一版画出来的齿轮像一排歪歪扭扭的锯齿,第二版齿轮倒是像样了,可十二个小齿轮转起来之后齿全对不上,啮合处互相穿模,看着像两把梳子互相啃。真正跑通是在我把齿数比、中心距、初相位这三件事拆开算清楚之后。这篇就把整个过程摊开讲:正十二边的顶点怎么和十二个小时刻度对上,齿轮的每一个坐标是怎么从齿数推出来的,内嵌的花样怎么用 Canvas 的分层缓存做到 60 帧不掉,以及我在调试阶段踩过的那些坑。适合已经会一点 Canvas 基础 API、想做一个有机械质感的桌面时钟或者表盘组件的朋友,也适合纯粹想看看"几何图形怎么变成会动的花样"的读者——代码是完整的,可以直接抄走改参数。
1. 为什么偏偏是正十二边形加齿轮
1.1 十二个顶点就是十二个小时
做表盘这件事,最省事的路径是找一张现成的表盘位图当底,指针叠在上面转。我一开始也这么干,效果不能说难看,但特别"平"——指针像贴在玻璃上滑,没有层次,也没有任何机械的味道。想把这种平去掉,就得让表盘本身有结构,而结构最直接的来源就是几何。
选正十二边形不是随手挑的。表盘的核心刻度是十二个小时,正十二边形正好有十二个顶点,顶点角度间隔 30 度,和时钟的小时间隔一模一样。这意味着我只要把多边形的第一个顶点放在 12 点方向,剩下十一个顶点自动落在 1 点到 11 点的位置上,刻度线、数字、装饰点全都可以挂在顶点上,不需要单独再去算一遍角度。这个对应关系是整张表盘的骨架,后面所有齿轮的方位、指针的长度比例、外圈的描边,全都建立在这个骨架上。
具体到坐标,顶点角度写成-π/2 + i * π/6(i 从 0 到 11)。之所以从-π/2起算,是因为 Canvas 的角度零度在三点方向,而屏幕坐标 y 轴向下,所以正角度是顺时针转。减掉