M1 MacBook Pro上JavaScript太空侵略者游戏运行过快问题求助
解决高刷新率屏幕下requestAnimationFrame游戏跑快的问题
核心问题是requestAnimationFrame的回调频率与屏幕刷新率绑定——M1 MacBook Pro的120Hz屏会让回调每秒触发120次,远高于旧设备的60Hz,而如果你的游戏逻辑依赖回调次数而非时间差更新,就会出现速度异常。以下是具体解决方法:
采用固定时间步长的逻辑更新(推荐)
彻底脱离屏幕刷新率的影响,基于时间差驱动游戏逻辑,确保无论设备帧率如何,游戏速度一致。实现思路是记录每次回调的时间戳,累积时间差,当累积值达到固定步长时执行逻辑更新:let lastTime = 0; const fixedStep = 1000 / 60; // 固定每秒60次逻辑更新,可根据需求调整 let accumulator = 0; function gameLoop(timestamp) { const delta = timestamp - lastTime; lastTime = timestamp; accumulator += delta; // 处理所有待执行的逻辑帧 while (accumulator >= fixedStep) { updateGame(); // 敌人移动、碰撞检测等核心逻辑都放这里 accumulator -= fixedStep; } // 可选:用剩余时间做插值渲染,让动画更平滑 const alpha = accumulator / fixedStep; renderGame(alpha); requestAnimationFrame(gameLoop); } requestAnimationFrame(gameLoop);这种方式既能保证逻辑速度稳定,又能利用高刷新率屏幕的优势让渲染更流畅。
应急方案:限制回调执行频率
如果不想大幅修改逻辑,可以在回调中判断时间间隔,只在达到目标帧率的时间差时才执行更新:let lastRender = 0; const targetInterval = 1000 / 60; // 目标60fps,对应16.67ms间隔 function gameLoop(timestamp) { if (timestamp - lastRender < targetInterval) { requestAnimationFrame(gameLoop); return; } updateGame(); renderGame(); lastRender = timestamp; requestAnimationFrame(gameLoop); } requestAnimationFrame(gameLoop);注意:这种方法会浪费高刷新率屏幕的性能,且动画平滑度不如固定时间步长方案。
排查原有帧率控制逻辑
你提到降到10fps仍过快,大概率是之前的控制只减少了渲染次数,但游戏逻辑仍在每次requestAnimationFrame回调中执行。比如每10次回调才渲染一次,但逻辑每秒跑120次,敌人移动速度自然是60Hz设备的两倍。必须确保逻辑更新和渲染都基于时间差,而非回调次数。
内容的提问来源于stack exchange,提问作者Sirab33
相关产品推荐
相关产品推荐

