88 lines
1.9 KiB
C++
88 lines
1.9 KiB
C++
|
#include "StarTickRateMonitor.hpp"
|
||
|
#include "StarTime.hpp"
|
||
|
|
||
|
namespace Star {
|
||
|
|
||
|
TickRateMonitor::TickRateMonitor(double window) : m_window(window) {
|
||
|
reset();
|
||
|
}
|
||
|
|
||
|
double TickRateMonitor::window() const {
|
||
|
return m_window;
|
||
|
}
|
||
|
|
||
|
void TickRateMonitor::reset() {
|
||
|
m_lastTick = Time::monotonicTime() - m_window;
|
||
|
m_ticks = 0;
|
||
|
}
|
||
|
|
||
|
double TickRateMonitor::tick(unsigned count) {
|
||
|
double currentTime = Time::monotonicTime();
|
||
|
|
||
|
if (m_lastTick > currentTime) {
|
||
|
m_lastTick = currentTime - m_window;
|
||
|
m_ticks = 0;
|
||
|
} else if (m_lastTick < currentTime) {
|
||
|
double timePast = currentTime - m_lastTick;
|
||
|
double rate = m_ticks / m_window;
|
||
|
m_ticks = max(0.0, m_ticks - timePast * rate);
|
||
|
m_lastTick = currentTime;
|
||
|
}
|
||
|
|
||
|
m_ticks += count;
|
||
|
|
||
|
return m_ticks / m_window;
|
||
|
}
|
||
|
|
||
|
double TickRateMonitor::rate() const {
|
||
|
return TickRateMonitor(*this).tick(0);
|
||
|
}
|
||
|
|
||
|
TickRateApproacher::TickRateApproacher(double targetTickRate, double window)
|
||
|
: m_tickRateMonitor(window), m_targetTickRate(targetTickRate) {}
|
||
|
|
||
|
double TickRateApproacher::window() const {
|
||
|
return m_tickRateMonitor.window();
|
||
|
}
|
||
|
|
||
|
void TickRateApproacher::setWindow(double window) {
|
||
|
if (window != m_tickRateMonitor.window()) {
|
||
|
m_tickRateMonitor = TickRateMonitor(window);
|
||
|
tick(m_targetTickRate * window);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
double TickRateApproacher::targetTickRate() const {
|
||
|
return m_targetTickRate;
|
||
|
}
|
||
|
|
||
|
void TickRateApproacher::setTargetTickRate(double targetTickRate) {
|
||
|
m_targetTickRate = targetTickRate;
|
||
|
}
|
||
|
|
||
|
void TickRateApproacher::reset() {
|
||
|
setWindow(window());
|
||
|
}
|
||
|
|
||
|
double TickRateApproacher::tick(unsigned count) {
|
||
|
return m_tickRateMonitor.tick(count);
|
||
|
}
|
||
|
|
||
|
double TickRateApproacher::rate() const {
|
||
|
return m_tickRateMonitor.rate();
|
||
|
}
|
||
|
|
||
|
double TickRateApproacher::ticksBehind() {
|
||
|
return (m_targetTickRate - m_tickRateMonitor.rate()) * window();
|
||
|
}
|
||
|
|
||
|
double TickRateApproacher::ticksAhead() {
|
||
|
return -ticksBehind();
|
||
|
}
|
||
|
|
||
|
double TickRateApproacher::spareTime() {
|
||
|
return ticksAhead() / m_targetTickRate;
|
||
|
}
|
||
|
|
||
|
}
|