1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-08-13 19:54:17 +02:00

Fix stuttering animations when using high frame rate limit or vsync

This commit is contained in:
Alexander Wilms
2023-09-26 22:53:45 +02:00
parent e33127a1f7
commit e2eeec96a9

View File

@@ -12,27 +12,36 @@
#include "FramerateManager.h"
#include "../../lib/CConfigHandler.h"
#include <SDL_video.h>
FramerateManager::FramerateManager(int targetFrameRate)
: targetFrameTime(Duration(boost::chrono::seconds(1)) / targetFrameRate)
, lastFrameIndex(0)
: lastFrameIndex(0)
, lastFrameTimes({})
, lastTimePoint(Clock::now())
, vsyncEnabled(settings["video"]["vsync"].Bool())
{
if(vsyncEnabled)
{
static int display_in_use = 0;
SDL_DisplayMode mode;
SDL_GetCurrentDisplayMode(display_in_use, &mode);
int displayRefreshRate = mode.refresh_rate;
logGlobal->info("Display refresh rate is %d", displayRefreshRate);
targetFrameTime = Duration(boost::chrono::seconds(1)) / displayRefreshRate;
} else
{
targetFrameTime = Duration(boost::chrono::seconds(1)) / targetFrameRate;
}
boost::range::fill(lastFrameTimes, targetFrameTime);
}
void FramerateManager::framerateDelay()
{
if(!vsyncEnabled)
{
Duration timeSpentBusy = Clock::now() - lastTimePoint;
Duration timeSpentBusy = Clock::now() - lastTimePoint;
// FPS is higher than it should be, then wait some time
if(timeSpentBusy < targetFrameTime)
boost::this_thread::sleep_for(targetFrameTime - timeSpentBusy);
}
// FPS is higher than it should be, then wait some time
if(timeSpentBusy < targetFrameTime)
boost::this_thread::sleep_for(targetFrameTime - timeSpentBusy);
// compute actual timeElapsed taking into account actual sleep interval
// limit it to 100 ms to avoid breaking animation in case of huge lag (e.g. triggered breakpoint)