上下文

起因是修复 一个 bug , 简单来说就是 滚动的时候文本会出现轻微的抖动,现象很奇怪

现象

仔细看 province city 区域 的文字,在滚动后 会出现轻微的抖动

图 0

问题代码

虚拟滚动条,在每次滚动后,需要同步滚动条和可视区域 的位置

图 1

看起来没啥问题,计算出偏移量是一个很精确的浮点数

图 2

最后,在 mdn 看到这样 一篇文章, 有这样的说明

图 3


子像素,我在有些文章看到又称为亚像素

Css Sub Pixel

在 css 中,浏览器是支持小数点的像素的,但是处理方式不同,我这里测试了下

width, padding , border 都是小数,以宽度为例,按照盒模型渲染预期结果:

132.34555 + 4.212377711 + 1.2 = 137.75792771099998

浏览器 (Chorme) 中,宽度实际渲染为 138

图 4


调试工具 Computed 结果

图 5

文字抖动原因

根据 MDN 的说明,当坐标是非整数的时候,浏览器默认会开启抗锯齿功能,尽可能的让元素平滑

由于 Canvas 中也是支持子像素的,所以我猜测实际浏览器也会像 CSS 一样,有一套自己的算法,类似于 将坐标小数点四舍五入

图 6


所以在我这个例子中,滚动偏移比如

第一次滚动偏移 342.9225376674107, 实际渲染 343

图 10

1
2
- 342.9225376674107
+ 343

第二次滚动偏移 670.256822374132, 实际渲染 670

图 9

1
2
- 670.256822374132
+ 670

所以在实际的情况,偏移量有可能大,有可能小,就会产生所谓抖动的现象

现在将算出来的偏移量进行取整,抖动的问题解决

图 8

2j5j8USWRjXr1fgYd7K_302270051889___hd.mp4 (321.04KB)

参考资料

canvas 的优化
html5-canvas-sprite-optimisation
sub-pixel-problems-in-css
为何 Canvas 内元素动画总是在颤抖?
Improving HTML5 Canvas Performance