Throttle Hz aligned to time-grid, add initial offset.
Allows sync of two or more FG session, if wall clock are in synch.
This commit is contained in:
parent
7dfbcf0918
commit
a28bf28ee0
2 changed files with 24 additions and 11 deletions
|
@ -116,6 +116,8 @@ void TimeManager::init()
|
||||||
_simTimeDelta = fgGetNode("sim/time/delta-sec", true);
|
_simTimeDelta = fgGetNode("sim/time/delta-sec", true);
|
||||||
_mpProtocolClockNode = fgGetNode("sim/time/mp-clock-sec", true);
|
_mpProtocolClockNode = fgGetNode("sim/time/mp-clock-sec", true);
|
||||||
_steadyClockNode = fgGetNode("sim/time/steady-clock-sec", true);
|
_steadyClockNode = fgGetNode("sim/time/steady-clock-sec", true);
|
||||||
|
_frameTimeOffsetNode = fgGetNode("sim/time/frame-time-offset-ms", true);
|
||||||
|
_dtRemainderNode = fgGetNode("sim/time/dt-remainder-sec", true);
|
||||||
_mpClockOffset = fgGetNode("sim/time/mp-clock-offset-sec", true);
|
_mpClockOffset = fgGetNode("sim/time/mp-clock-offset-sec", true);
|
||||||
_steadyClockDrift = fgGetNode("sim/time/steady-clock-drift-ms", true);
|
_steadyClockDrift = fgGetNode("sim/time/steady-clock-drift-ms", true);
|
||||||
_computeDrift = fgGetNode("sim/time/compute-clock-drift", true);
|
_computeDrift = fgGetNode("sim/time/compute-clock-drift", true);
|
||||||
|
@ -150,6 +152,8 @@ void TimeManager::unbind()
|
||||||
_simTimeDelta.clear();
|
_simTimeDelta.clear();
|
||||||
_mpProtocolClockNode.clear();
|
_mpProtocolClockNode.clear();
|
||||||
_steadyClockNode.clear();
|
_steadyClockNode.clear();
|
||||||
|
_frameTimeOffsetNode.clear();
|
||||||
|
_dtRemainderNode.clear();
|
||||||
_mpClockOffset.clear();
|
_mpClockOffset.clear();
|
||||||
_steadyClockDrift.clear();
|
_steadyClockDrift.clear();
|
||||||
_computeDrift.clear();
|
_computeDrift.clear();
|
||||||
|
@ -211,6 +215,10 @@ void TimeManager::computeTimeDeltas(double& simDt, double& realDt)
|
||||||
const double systemStamp = _systemStamp.toSecs();
|
const double systemStamp = _systemStamp.toSecs();
|
||||||
_steadyClock = floor(systemStamp * modelHz) / modelHz;
|
_steadyClock = floor(systemStamp * modelHz) / modelHz;
|
||||||
|
|
||||||
|
// add offset if defined
|
||||||
|
const double frameOffsetMsec = _frameTimeOffsetNode->getDoubleValue();
|
||||||
|
_steadyClock += frameOffsetMsec / 1000.0;
|
||||||
|
|
||||||
// initialize the remainder with offset from the system clock
|
// initialize the remainder with offset from the system clock
|
||||||
_dtRemainder = systemStamp - _steadyClock;
|
_dtRemainder = systemStamp - _steadyClock;
|
||||||
|
|
||||||
|
@ -293,6 +301,7 @@ void TimeManager::computeTimeDeltas(double& simDt, double& realDt)
|
||||||
_steadyClock += mpProtocolDt;
|
_steadyClock += mpProtocolDt;
|
||||||
_mpProtocolClock = _steadyClock + _mpClockOffset->getDoubleValue();
|
_mpProtocolClock = _steadyClock + _mpClockOffset->getDoubleValue();
|
||||||
|
|
||||||
|
_dtRemainderNode->setDoubleValue(_dtRemainder);
|
||||||
_steadyClockNode->setDoubleValue(_steadyClock);
|
_steadyClockNode->setDoubleValue(_steadyClock);
|
||||||
_mpProtocolClockNode->setDoubleValue(_mpProtocolClock);
|
_mpProtocolClockNode->setDoubleValue(_mpProtocolClock);
|
||||||
|
|
||||||
|
@ -376,18 +385,20 @@ void TimeManager::computeFrameRate()
|
||||||
|
|
||||||
void TimeManager::throttleUpdateRate()
|
void TimeManager::throttleUpdateRate()
|
||||||
{
|
{
|
||||||
double throttle_hz = _maxFrameRate->getDoubleValue();
|
const double throttleHz = _maxFrameRate->getDoubleValue();
|
||||||
|
|
||||||
// no delay required.
|
// no delay required.
|
||||||
if (throttle_hz <= 0)
|
if (throttleHz <= 0) {
|
||||||
{
|
|
||||||
_frameWait->setDoubleValue(0);
|
_frameWait->setDoubleValue(0);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const double modelHz = _modelHz->getDoubleValue();
|
||||||
SGTimeStamp frameWaitStart = SGTimeStamp::now();
|
SGTimeStamp frameWaitStart = SGTimeStamp::now();
|
||||||
|
|
||||||
// sleep for exactly 1/hz seconds relative to the past valid timestamp
|
// we want to sleep until just after the next ideal timestamp wanted, we will
|
||||||
SGTimeStamp::sleepUntil(_lastStamp + SGTimeStamp::fromSec(1 / throttle_hz));
|
// gain time from a 1/Hz step if the last timestamp was late.
|
||||||
|
const double t = (round(modelHz / throttleHz) / modelHz) - _dtRemainder;
|
||||||
|
SGTimeStamp::sleepUntil(_lastStamp + SGTimeStamp::fromSec(t));
|
||||||
_frameWait->setDoubleValue(frameWaitStart.elapsedMSec());
|
_frameWait->setDoubleValue(frameWaitStart.elapsedMSec());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -91,6 +91,8 @@ private:
|
||||||
SGPropertyNode_ptr _simTimeFactor;
|
SGPropertyNode_ptr _simTimeFactor;
|
||||||
SGPropertyNode_ptr _mpProtocolClockNode;
|
SGPropertyNode_ptr _mpProtocolClockNode;
|
||||||
SGPropertyNode_ptr _steadyClockNode;
|
SGPropertyNode_ptr _steadyClockNode;
|
||||||
|
SGPropertyNode_ptr _frameTimeOffsetNode;
|
||||||
|
SGPropertyNode_ptr _dtRemainderNode;
|
||||||
SGPropertyNode_ptr _mpClockOffset;
|
SGPropertyNode_ptr _mpClockOffset;
|
||||||
SGPropertyNode_ptr _steadyClockDrift;
|
SGPropertyNode_ptr _steadyClockDrift;
|
||||||
SGPropertyNode_ptr _computeDrift;
|
SGPropertyNode_ptr _computeDrift;
|
||||||
|
|
Loading…
Add table
Reference in a new issue