Canvas动画需用requestAnimationFrame递归驱动逐帧循环,因其同步屏幕刷新、省电精准;清屏后须重置绘图状态,小球运动需手动更新坐标并微调反弹位置,图片必须加载完成才能绘制。
Canvas 动画不是加个 animation CSS 属性就能跑起来的,它必须靠 JavaScript 主动清屏、重绘、更新状态,核心是 requestAnimationFrame 驱动的逐帧循环。
setTimeout 或 setInterval
它们不和屏幕刷新率同步,容易掉帧、时间漂移,切到后台还继续执行耗电。而 requestAnimationFrame 会自动对齐显示器刷新节奏(通常是 60fps),且页面不可见时暂停,更省电也更准。
常见错误是只调一次:requestAnimationFrame(draw),结果动画只画一帧就停了。
clearRect 清屏后图形还残留?因为 clearRect 只擦像素,不重置绘图状态。如果上一帧设置了 ctx.globalAlpha = 0.5 或 ctx.lineWidth = 4,下一帧继续画,就会叠加变糊、变粗、变深。
立即学习“前端免费学习笔记(深入)”;
ctx.clearRect(0, 0, canvas.width, canvas.height)
ctx.globalAlpha = 1、ctx.setTransform(1, 0, 0, 1, 0, 0)
save()/restore(),开销大;优先用 setTransform 重置变换矩阵clearRect(x, y, w, h) 擦“脏区域”,但需自己算包围矩形Canvas 不管对象,所有运动都靠你手动算坐标。最简模型就是每帧给 x、y 加上速度 vx、vy,碰到边缘翻转方向。
vx = 2),用小数(vx = 2.3)才能平滑;整数容易因像素对齐抖动=== 0,要用 <= 0 或 >= canvas.width - diameter,否则高速下会跳过临界帧x = 0; vx = -Math.abs(vx),防止卡在边缘反复触发判定draw 前调 beginPath(),否则多条路径连成一团真正容易被忽略的是:动画逻辑一旦涉及图片(drawImage),90% 的黑屏、错位、报错(如 Failed to execute 'drawImage': The image argument is a canvas element with a width or height of 0)都源于图片还没加载完就绘制——必须等 img.onload 触发后再启动循环,或用 img.complete 做前置判断。