EJanuszewski

Framerate issues at 144hz

Recommended Posts

Hi all, I'm pretty new to this and I'm only really a beginner JavaScript developer too so sorry for potentially being naive.

I can't share code as I'm not at my PC now but essentially I've got a mesh that I'm moving with the arrow keys, (player.position.x += .1; as an example) however on my 144hz monitor it moves twice as fast due to running more frames, does anyone know what the solution to this would be, or point me in the right direction and I'd love to try solve it myself.

Cheers,

Edward

Share this post


Link to post
Share on other sites

Don't think it's really the monitor? I understood he tried on two different computers - one with better specs (and the better monitor) and one on a lower one? That was just my guess  ;)

Share this post


Link to post
Share on other sites

The monitor actually won't make any difference - the rendering is using requestAnimatonFrame, which limits the FPS to 60 FPS max - independent if your monitor has 50, 100 or 144Hz.

Share this post


Link to post
Share on other sites

The monitor actually won't make any difference - the rendering is using requestAnimatonFrame, which limits the FPS to 60 FPS max - independent if your monitor has 50, 100 or 144Hz.

To quote Mozilla's docs: "The number of callbacks is usually 60 times per second, but will generally match the display refresh rate in most web browsers as per W3C recommendation." https://developer.mozilla.org/en/docs/Web/API/window/requestAnimationFrame

I believe the standard offers no promise that rAF will max out at 60Hz, and instead that browsers are encouraged to sync to the refresh rate of the video mode (it just happens that 60Hz is somewhat common)

Share this post


Link to post
Share on other sites

I've got a mesh that I'm moving with the arrow keys, (player.position.x += .1; as an example) however on my 144hz monitor it moves twice as fast due to running more frames, 

 

Short answer: Many games solve this problem by doing "game rules" (processing inputs, doing physics, etc.) in one loop and rendering in another. The idea is that your game rules should probably use a fixed timestep - you don't want physics behaving differently on slow and fast machines - but the render loop can run as fast as the player's machine will go.

 

Long answer - go read this article right now! Required game developer reading in my humble opinion.  :)

Share this post


Link to post
Share on other sites

For my game I just run both loops in the same thread, it's pretty straightforward. The render loop runs off RAF like normal, and for the tick loop, I call it at 30fps and I always always pass it dt=33ms, regardless of how long it's really been since the last tick.

Share this post


Link to post
Share on other sites

@fenomas : what do you mean with "I call it at 30fps and I always always pass it dt=33ms" ?

Do you simply use some JS setInterval() or do you manage your own ticks with some embedded loops (so you get your own time measures) ?

Share this post


Link to post
Share on other sites

jerome: It took me a while to figure it all out, but basically I have functions like:

function tick(dt) {   // step game world forward in time by tick_time}function render(tick_dt) {   // for each mesh: position += velocity * tick_dt   // render world}

tick() does things like step the physics engine, handle the AI, apply game rules, etc. The function takes a time step but I always pass it a fixed amount. render() renders the state of the world (including calling BJS render). Note that the render function also takes a dt, and moves meshes along their velocities a little - this lets you run physics less often and still get smooth movement.

 

As for how I call the functions, I use a handy library called game-shell that manages the timing, along with other features. But I think it would work just as well to do use a setInterval for tick() and an RAF loop for render().

Share this post


Link to post
Share on other sites

Just a follow up on this, scene.getAnimationRatio(); seems to do the job  :)

 

So as for tick, as I need the same thing are you saying I can just run a setInterval outside of the runRenderLoop? Do you happen to have a code example you can share?

Share this post


Link to post
Share on other sites

Like I said I use that game-shell library, and it manages the timings for me. To do it manually, I would do something like this:

var tick_time = 40  // desired ms between ticks.. 40 would be for 25 ticks/secondfunction RAF() {   var now = performance.now()   var dt = now - _last   _last = now   if (game_paused) { return }      accumulator += dt   if (accumulator > tick_time) {       accumulator -= tick_time       game.tick(tick_time)       last_tick = now   }   var time_since_tick = now - last_tick   game.render(time_since_tick)   requestAnimationFrame(RAF)}

That's off the top of my head, but something along those lines. Note that I don't pass dt to the tick function, I pass a constant value so that I get fixed timesteps. The accumulator variable is so that you get the right number of ticks over the long run, and the time_since_tick variable being passed to the render function is so that it can update mesh positions (assuming they're driven by key inputs or a physics engine.. for a plain animation I guess this would work differently).

 

Does that make any sense? 

Share this post


Link to post
Share on other sites

Nice

 

and what are the pro/con compared to an equivalent of tick() just called by a simple setInterval() indepedant from the RAF of course ?

 

I mean :

  • render only in the requestAnimationFrame() callback
  • physics, AI, controls, etc in the setInterval() callback

say, with setInterval called every 33 ms for instance

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...

  • Recently Browsing   0 members

    No registered users viewing this page.