geckosio / phaser-on-nodejs

Allows you to run Phaser 3 game (including Phaser's physics engines) on Node.js
MIT License
102 stars 11 forks source link

Target framerate not considering delta time #14

Closed hubertgrzeskowiak closed 1 month ago

hubertgrzeskowiak commented 2 years ago

At the moment, the main loop consists of the animationFrame function that seems to always delay the next frame by a static number of milliseconds. By default this is around 16.7ms with 60FPS.

const animationFrame = (cb: any) => {
  if (typeof cb !== 'function') return 0 // this line saves a lot of cpu
  window.setTimeout(() => cb(0), 1000 / global.phaserOnNodeFPS)
  return 0
}

window.requestAnimationFrame = cb => {
  return animationFrame(cb)
}

Doesn't this assume that the frame calculation takes 0ms? If the frame calculation would take say 100ms for some reason, the main loop would still wait for 16.7ms before calling the next step, right?

For reference, there is a polyfill definition of animationFrame in Phaser at https://github.com/photonstorm/phaser/blob/5c8ecbcf999e6f328d21884e877c9e5935d2d350/src/polyfills/requestAnimationFrame.js that seems to take the time since last frame into consideration.

I must be missing something. I can't be possibly the first person to notice this, right?

hubertgrzeskowiak commented 2 years ago

Please let me know your thoughts and if my assumption is correct, I'm happy to put up a PR.

snatvb commented 2 years ago

No, if your javascript will take 100ms, then your code in requestAnimationFrame will be called after that, without additional time and polyfill work same

setTimeout runs timeout in C++ thread and after done will write task to queue, when your eventloop will run tasks it will call 16 + lastTime - currentTime; - 16 is frame time in 60fps, with the calculations you can get 16ms in maximum and less than 0ms in minimum, but there is such lines:

        if (delay < 0)
        {
            delay = 0;
        }

and you will get timeout with 0-16ms delay time

if your js will take more than 0ms, this time will be subtracted :)