requestAnimationFrame(rAF)是实现JavaScript动画最推荐的方式,它由浏览器调度、与屏幕刷新率同步(通常60fps),比setTimeout/setInterval更高效流畅省电;其回调自动传入时间戳,需手动递归调用以实现循环动画,后台标签页会自动降频。

JavaScript 实现动画效果的核心是让元素的样式在短时间内连续、平滑地变化,而 requestAnimationFrame(简称 rAF)是现代 Web 中最推荐的方式——它由浏览器调度,与屏幕刷新率同步(通常 60fps),比 setTimeout 或 setInterval 更高效、更流畅、更省电。
requestAnimationFrame 的基本用法
rAF 接收一个回调函数作为参数,浏览器会在下一次重绘前执行该函数。它返回一个整数 ID,可用于取消动画(配合 cancelAnimationFrame)。
关键点:
- 回调函数会自动传入一个时间戳(DOMHighResTimeStamp),表示当前帧开始的时间(毫秒级,精确到微秒)
- 它不是自动循环的——想实现持续动画,需在回调内部再次调用
requestAnimationFrame - 页面处于后台标签页时,rAF 会自动降频或暂停,节省资源
写一个简单的位移动画
比如让一个 立即学习“Java免费学习笔记(深入)”; function animate(currentTime) {
if (!startTime) startTime = currentTime;
const elapsed = currentTime - startTime;
const progress = Math.min(elapsed / duration, 1); // 防止超限
const x = startX + (endX - startX) * progress; box.style.transform = if (progress < 1) {
requestAnimationFrame(animate);
}
} requestAnimationFrame(animate);
为避免每次手写时间计算,可以封装一个简易的 支持:起始值、目标值、缓动函数、完成回调 }
requestAnimationFrame(step);
} // 使用示例:给 opacity 做淡入
animate({
from: 0,
to: 1,
duration: 800,
easing: t => t * t, // 缓入
onUpdate: val => box.style.opacity = val,
onComplete: () => console.log('动画完成')
});
rAF 适合需要 JavaScript 动态控制的场景,例如: 而纯展示型、声明式的动画(如按钮悬停、页面切换),优先使用 CSS const box = document.getElementById('box');
let startTime = null;
const duration = 2000; // 动画总时长 2s
const startX = 0;
const endX = 400;
translateX(${x}px);封装可复用的动画函数
animate 工具函数:function animate({ from, to, duration = 300, easing = t => t, onUpdate, onComplete }) {
const start = performance.now();
function step(current) {
const elapsed = current - start;
const progress = Math.min(elapsed / duration, 1);
const value = from + (to - from) * easing(progress);
onUpdate(value);
if (progress < 1) {
requestAnimationFrame(step);
} else if (onComplete) {
onComplete();
}和 CSS 动画/transition 的区别与选择
transition 或 @keyframes——它们由 GPU 加速,性能更好,代码更简洁,且天然支持硬件加速和系统偏好(如减少动画)。










