Search code examples
c++windowsframe-rate

How do I achieve an average of 60 (or 30, or some other number) FPS without access to vblank?


How do I achieve an average of say, 60, (or 30) FPS in my game without access to the vertical retrace interrupt? (Some drivers don't provide vblank interrupt.)

I don't want to waste CPU time blitting frames faster than the monitor can display anyway, but at the same time I don't want to let the average frame rate drop much lower than the monitor display rate, since that would deprive the player of timely feedback.

I am using OpenGL, but the principle should be the same for GDI or just about anything. I don't care primarily about avoiding tearing, but rather keeping the illusion of realtime control, that is the combined input and output lag low.

I am sure there must be some kind of standard pattern for this. (Periodic timers? Sleep?) I am using Windows (pre--Metro) but more generic ideas are very welcome too.


Solution

  • The comment you added made it more explicit that you are concerned about tearing: Obviously you should use double buffering which you activate when you call ChoosePixelFormat() but you still have to get the timing right to have no tearing:

    • redraw immediately after your call to SwapBuffers(). This gives you 1/60th second; if you need more you have to drop down to eg 30fps temporarily.

    • you CAN call the next SwapBuffers immediately, but if you do that you would consume 100% cpu, because as of point 1 you should redraw the backbuffer immediately after it. To avoid it you should try to sleep if enough time remains, eg use QueryPerformanceCounter/Frequency to determine how much time is left until the next 1/60th second: if it is more than eg 8 millis then Sleep(1), else busy-wait to not make the framerate vary too much.