Skip to content
This repository has been archived by the owner on Apr 15, 2023. It is now read-only.

Commit

Permalink
[added] Display latency correction based on refresh rate via advanced…
Browse files Browse the repository at this point in the history
…settings.xml
  • Loading branch information
Istvan Stikrad committed Feb 24, 2012
1 parent 830d43c commit 180c2d2
Show file tree
Hide file tree
Showing 6 changed files with 84 additions and 3 deletions.
14 changes: 14 additions & 0 deletions xbmc/cores/VideoRenderers/RenderManager.cpp
Expand Up @@ -103,6 +103,7 @@ CXBMCRenderManager::CXBMCRenderManager()
m_presentmethod = PRESENT_METHOD_SINGLE;
m_bReconfigured = false;
m_hasCaptures = false;
m_displayLatency = 0.0f;
}

CXBMCRenderManager::~CXBMCRenderManager()
Expand Down Expand Up @@ -320,6 +321,8 @@ unsigned int CXBMCRenderManager::PreInit()
#endif
}

UpdateDisplayLatency();

return m_pRenderer->PreInit();
}

Expand Down Expand Up @@ -712,6 +715,17 @@ void CXBMCRenderManager::Recover()
#if defined(HAS_GL) && !defined(TARGET_DARWIN)
glFlush(); // attempt to have gpu done with pixmap and vdpau
#endif

UpdateDisplayLatency();
}

void CXBMCRenderManager::UpdateDisplayLatency()
{
float refresh = g_graphicsContext.GetFPS();
if (g_graphicsContext.GetVideoResolution() == RES_WINDOW)
refresh = 0; // No idea about refresh rate when windowed, just get the default latency
m_displayLatency = (double) g_advancedSettings.GetDisplayLatency(refresh);
CLog::Log(LOGDEBUG, "CRenderManager::UpdateDisplayLatency - Latency set to %1.0f msec", m_displayLatency * 1000.0f);
}

void CXBMCRenderManager::UpdateResolution()
Expand Down
3 changes: 3 additions & 0 deletions xbmc/cores/VideoRenderers/RenderManager.h
Expand Up @@ -108,6 +108,7 @@ class CXBMCRenderManager
float GetMaximumFPS();
inline bool Paused() { return m_bPauseDrawing; };
inline bool IsStarted() { return m_bIsStarted;}
double GetDisplayLatency() { return m_displayLatency; }

bool Supports(ERENDERFEATURE feature)
{
Expand Down Expand Up @@ -216,6 +217,8 @@ class CXBMCRenderManager
PRESENT_METHOD_BOB,
};

double m_displayLatency;
void UpdateDisplayLatency();

double m_presenttime;
double m_presentcorr;
Expand Down
2 changes: 1 addition & 1 deletion xbmc/cores/dvdplayer/DVDPlayer.cpp
Expand Up @@ -2433,7 +2433,7 @@ void CDVDPlayer::GetGeneralInfo(CStdString& strGeneralInfo)
{
if (!m_bStop)
{
double dDelay = (double)m_dvdPlayerVideo.GetDelay() / DVD_TIME_BASE;
double dDelay = m_dvdPlayerVideo.GetDelay() / DVD_TIME_BASE - g_renderManager.GetDisplayLatency();

double apts = m_dvdPlayerAudio.GetCurrentPts();
double vpts = m_dvdPlayerVideo.GetCurrentPts();
Expand Down
4 changes: 2 additions & 2 deletions xbmc/cores/dvdplayer/DVDPlayerVideo.cpp
Expand Up @@ -1111,8 +1111,8 @@ int CDVDPlayerVideo::OutputPicture(const DVDVideoPicture* src, double pts)
pts -= DVD_TIME_BASE * interval;
}

//User set delay
pts += m_iVideoDelay;
// Correct pts by user set delay and rendering delay
pts += m_iVideoDelay - DVD_SEC_TO_TIME(g_renderManager.GetDisplayLatency());

// calculate the time we need to delay this picture before displaying
double iSleepTime, iClockSleep, iFrameSleep, iPlayingClock, iCurrentClock, iFrameDuration;
Expand Down
51 changes: 51 additions & 0 deletions xbmc/settings/AdvancedSettings.cpp
Expand Up @@ -540,6 +540,44 @@ void CAdvancedSettings::ParseSettingsFile(const CStdString &file)
XMLUtils::GetBoolean(pElement,"forcedxvarenderer", m_DXVAForceProcessorRenderer);
//0 = disable fps detect, 1 = only detect on timestamps with uniform spacing, 2 detect on all timestamps
XMLUtils::GetInt(pElement, "fpsdetect", m_videoFpsDetect, 0, 2);

// Store global display latency settings
m_videoDefaultLatency = 0;
TiXmlElement* pVideoLatency = pElement->FirstChildElement("latency");
if (pVideoLatency)
{
float refresh, refreshmin, refreshmax, delay;
TiXmlElement* pRefreshVideoLatency = pVideoLatency->FirstChildElement("refresh");

while (pRefreshVideoLatency)
{
RefreshVideoLatency videolatency = {0};

if (XMLUtils::GetFloat(pRefreshVideoLatency, "rate", refresh))
{
videolatency.refreshmin = refresh - 0.01f;
videolatency.refreshmax = refresh + 0.01f;
}
else if (XMLUtils::GetFloat(pRefreshVideoLatency, "min", refreshmin) &&
XMLUtils::GetFloat(pRefreshVideoLatency, "max", refreshmax))
{
videolatency.refreshmin = refreshmin;
videolatency.refreshmax = refreshmax;
}
if (XMLUtils::GetFloat(pRefreshVideoLatency, "delay", delay, -600.0f, 600.0f))
videolatency.delay = delay;

if (videolatency.refreshmin > 0.0f && videolatency.refreshmax >= videolatency.refreshmin)
m_videoRefreshLatency.push_back(videolatency);
else
CLog::Log(LOGWARNING, "Ignoring malformed display latency <refresh> entry, min:%f max:%f", videolatency.refreshmin, videolatency.refreshmax);

pRefreshVideoLatency = pRefreshVideoLatency->NextSiblingElement("refresh");
}

// Get default global display latency
XMLUtils::GetFloat(pVideoLatency, "delay", m_videoDefaultLatency, -600.0f, 600.0f);
}
}

pElement = pRootElement->FirstChildElement("musiclibrary");
Expand Down Expand Up @@ -1049,3 +1087,16 @@ void CAdvancedSettings::AddSettingsFile(const CStdString &filename)
{
m_settingsFiles.push_back(filename);
}

float CAdvancedSettings::GetDisplayLatency(float refreshrate)
{
float delay = m_videoDefaultLatency / 1000.0f;
for (int i = 0; i < (int) m_videoRefreshLatency.size(); i++)
{
RefreshVideoLatency& videolatency = m_videoRefreshLatency[i];
if (refreshrate >= videolatency.refreshmin && refreshrate <= videolatency.refreshmax)
delay = videolatency.delay / 1000.0f;
}

return delay; // in seconds
}
13 changes: 13 additions & 0 deletions xbmc/settings/AdvancedSettings.h
Expand Up @@ -59,6 +59,15 @@ struct RefreshOverride
bool fallback;
};


struct RefreshVideoLatency
{
float refreshmin;
float refreshmax;

float delay;
};

typedef std::vector<TVShowRegexp> SETTINGS_TVSHOWLIST;

class CAdvancedSettings
Expand Down Expand Up @@ -125,6 +134,8 @@ class CAdvancedSettings
bool m_videoAllowMpeg4VDPAU;
bool m_videoAllowMpeg4VAAPI;
std::vector<RefreshOverride> m_videoAdjustRefreshOverrides;
std::vector<RefreshVideoLatency> m_videoRefreshLatency;
float m_videoDefaultLatency;
bool m_videoDisableBackgroundDeinterlace;
int m_videoCaptureUseOcclusionQuery;
bool m_DXVACheckCompatibility;
Expand Down Expand Up @@ -303,6 +314,8 @@ class CAdvancedSettings
bool m_enableMultimediaKeys;
std::vector<CStdString> m_settingsFiles;
void ParseSettingsFile(const CStdString &file);

float GetDisplayLatency(float refreshrate);
};

XBMC_GLOBAL(CAdvancedSettings,g_advancedSettings);

0 comments on commit 180c2d2

Please sign in to comment.