You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在requestAnimationFrame中调整FPS且不加速游戏运行?

实现可自定义FPS且保证游戏速度不变的动画循环

核心思路

requestAnimationFrame的回调频率和显示器刷新率绑定(通常60Hz),没法直接指定帧率。要实现自定义FPS,得在循环里通过时间差判断,只在达到目标帧率的间隔时才执行游戏逻辑和渲染;同时游戏逻辑必须基于时间增量计算,而不是每帧固定变化量,这样不管帧率高低,游戏速度都一致。

具体实现步骤

1. 定义时间控制变量

需要几个变量来跟踪时间状态:

  • targetFPS:用户可设置的目标帧率(比如60、30、15)
  • frameInterval:每帧的间隔时间(计算方式:1000ms / targetFPS)
  • lastTime:上一次执行游戏逻辑的时间
  • deltaTime:累计未处理的时间(用来应对卡顿,避免游戏跳帧)

2. 修改动画循环函数

把原函数改成基于时间判断的逻辑:

let targetFPS = 60; // 用户可通过交互修改这个值,比如下拉框选择
let frameInterval = 1000 / targetFPS;
let lastTime = performance.now();
let deltaTime = 0;

function animate4(currentTime) {
  // 计算当前与上次的时间差,累加到deltaTime
  deltaTime += currentTime - lastTime;
  lastTime = currentTime;

  // 当累计时间超过帧间隔时,循环处理逻辑(应对卡顿场景)
  while (deltaTime >= frameInterval) {
    ctx.clearRect(0, 0, cw, ch);

    // 给每个游戏层传入时间增量,让逻辑基于时间计算
    gamearray.forEach((layer) => {
      layer.update(deltaTime);
    });

    // 减去已处理的帧间隔时间
    deltaTime -= frameInterval;
  }

  if (pause === true) { // 注意原代码拼写错误:paause → pause
    return;
  }
  requestAnimationFrame(animate4);
}

// 启动动画,传入初始时间
requestAnimationFrame(animate4);

3. 改造游戏逻辑的update方法

原来的layer.update()如果是每帧固定变化(比如layer.x += 5),要改成基于时间增量的计算,保证每秒变化量一致:

// 示例:原来的固定帧更新(60FPS时每秒移动300px,30FPS时变成150px,速度变慢)
// layer.update = function() {
//   this.x += 5;
// }

// 改成基于时间的更新(不管帧率,每秒固定移动300px)
layer.update = function(deltaTime) {
  // 每秒移动300像素 → 每毫秒移动0.3像素
  this.x += 0.3 * deltaTime;
}

4. 允许用户动态修改FPS

添加一个函数,让用户选择FPS时更新参数:

function setFPS(fps) {
  targetFPS = fps;
  frameInterval = 1000 / targetFPS;
}

// 示例:用户选择30FPS时调用
setFPS(30);

关键细节说明

  • while循环处理卡顿:用while而不是if,是为了应对页面卡顿的情况。比如卡顿100ms,目标FPS30(间隔33.33ms),此时deltaTime会累计到100,循环3次处理逻辑,避免游戏状态跳变。
  • 时间增量的作用:所有游戏逻辑(移动、动画、技能冷却等)都要基于deltaTime计算,这样帧率变化时,每秒的实际变化量不变,游戏速度就不会受影响。
  • requestAnimationFrame的优势:即使我们控制了帧率,依然用requestAnimationFrame驱动循环,因为它会和浏览器渲染同步,避免不必要的绘制,节省性能。

内容的提问来源于stack exchange,提问作者7A7z

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.02 21:30:10