aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBastien Bouclet2018-01-01 05:40:41 +0100
committerBastien Bouclet2018-01-27 18:12:34 +0100
commit3b50b57f544cb7c719a5f02f061853e10885ae6c (patch)
tree12a1aed649f42b4b45f16389577e403f9b67daef
parentd5d1229ae303030c4a478504f86e4eefad2ccc11 (diff)
downloadscummvm-rg350-3b50b57f544cb7c719a5f02f061853e10885ae6c.tar.gz
scummvm-rg350-3b50b57f544cb7c719a5f02f061853e10885ae6c.tar.bz2
scummvm-rg350-3b50b57f544cb7c719a5f02f061853e10885ae6c.zip
GUI: Rework the frame limiter to actually reach the target framerate
The previous combination of a fixed 10 milliseconds delay and time since last update checks meant that in most cases 20 milliseconds elapsed between two calls to updateScreen resulting in a 50 fps framerate. On systems with wait for vsync enabled that meant that some frames were missed. The new frame limiter waits for a variable delay equal to the non consumed time in the slot allocated to the frame.
-rw-r--r--gui/gui-manager.cpp30
1 files changed, 11 insertions, 19 deletions
diff --git a/gui/gui-manager.cpp b/gui/gui-manager.cpp
index 76f557711d..2e947c6f32 100644
--- a/gui/gui-manager.cpp
+++ b/gui/gui-manager.cpp
@@ -299,10 +299,11 @@ void GuiManager::runLoop() {
}
Common::EventManager *eventMan = _system->getEventManager();
- uint32 lastRedraw = 0;
- const uint32 waitTime = 1000 / 60;
+ const uint32 targetFrameDuration = 1000 / 60;
while (!_dialogStack.empty() && activeDialog == getTopDialog() && !eventMan->shouldQuit()) {
+ uint32 frameStartTime = _system->getMillis(true);
+
redraw();
// Don't "tickle" the dialog until the theme has had a chance
@@ -312,14 +313,6 @@ void GuiManager::runLoop() {
if (_useStdCursor)
animateCursor();
-// _theme->updateScreen();
-// _system->updateScreen();
-
- if (lastRedraw + waitTime < _system->getMillis(true)) {
- lastRedraw = _system->getMillis(true);
- _theme->updateScreen();
- _system->updateScreen();
- }
Common::Event event;
@@ -349,13 +342,6 @@ void GuiManager::runLoop() {
}
processEvent(event, activeDialog);
-
-
- if (lastRedraw + waitTime < _system->getMillis(true)) {
- lastRedraw = _system->getMillis(true);
- _theme->updateScreen();
- _system->updateScreen();
- }
}
// Delete GuiObject that have been added to the trash for a delayed deletion
@@ -379,8 +365,14 @@ void GuiManager::runLoop() {
}
}
- // Delay for a moment
- _system->delayMillis(10);
+ _theme->updateScreen();
+
+ // Delay until the allocated frame time is elapsed to match the target frame rate
+ uint32 actualFrameDuration = _system->getMillis(true) - frameStartTime;
+ if (actualFrameDuration < targetFrameDuration) {
+ _system->delayMillis(targetFrameDuration - actualFrameDuration);
+ }
+ _system->updateScreen();
}
// WORKAROUND: When quitting we might not properly close the dialogs on