From 848f54d4a77f38a234ec2facdb5eefd1442bc1b4 Mon Sep 17 00:00:00 2001 From: Klaus Basan Date: Thu, 16 May 2019 14:43:11 +0200 Subject: [PATCH] Ref T668, clamp time fraction [0,1] --- src/blackmisc/simulation/interpolatorfunctions.h | 6 ++++++ src/blackmisc/simulation/interpolatorlinear.cpp | 15 ++++++++------- src/blackmisc/simulation/interpolatorpbh.cpp | 5 ++++- 3 files changed, 18 insertions(+), 8 deletions(-) diff --git a/src/blackmisc/simulation/interpolatorfunctions.h b/src/blackmisc/simulation/interpolatorfunctions.h index fc5f13504..df7a5c5cc 100644 --- a/src/blackmisc/simulation/interpolatorfunctions.h +++ b/src/blackmisc/simulation/interpolatorfunctions.h @@ -21,6 +21,12 @@ namespace BlackMisc return timeFraction >= 0.0 && timeFraction <= 1.0; } + //! Valid time fraction [0,1], this allows minor overshooting + inline bool isAcceptableTimeFraction(double timeFraction) + { + return timeFraction >= 0.0 && timeFraction <= 1.01; + } + //! Clamp time fraction [0,1] inline double clampValidTimeFraction(double timeFraction) { diff --git a/src/blackmisc/simulation/interpolatorlinear.cpp b/src/blackmisc/simulation/interpolatorlinear.cpp index ec0759311..ec2708e9c 100644 --- a/src/blackmisc/simulation/interpolatorlinear.cpp +++ b/src/blackmisc/simulation/interpolatorlinear.cpp @@ -66,14 +66,15 @@ namespace BlackMisc { BLACK_VERIFY_X(CAircraftSituation::isValidVector(oldVec), Q_FUNC_INFO, "Invalid old vector"); BLACK_VERIFY_X(CAircraftSituation::isValidVector(newVec), Q_FUNC_INFO, "Invalid new vector"); - BLACK_VERIFY_X(isValidTimeFraction(m_simulationTimeFraction), Q_FUNC_INFO, "Invalid fraction"); + BLACK_VERIFY_X(isAcceptableTimeFraction(m_simulationTimeFraction), Q_FUNC_INFO, "Invalid fraction"); } // Interpolate position: pos = (posB - posA) * t + posA CCoordinateGeodetic newPosition; - newPosition.setNormalVector((newVec[0] - oldVec[0]) * m_simulationTimeFraction + oldVec[0], - (newVec[1] - oldVec[1]) * m_simulationTimeFraction + oldVec[1], - (newVec[2] - oldVec[2]) * m_simulationTimeFraction + oldVec[2]); + const double tf = clampValidTimeFraction(m_simulationTimeFraction); + newPosition.setNormalVector((newVec[0] - oldVec[0]) * tf + oldVec[0], + (newVec[1] - oldVec[1]) * tf + oldVec[1], + (newVec[2] - oldVec[2]) * tf + oldVec[2]); if (CBuildConfig::isLocalDeveloperDebugBuild()) { @@ -86,7 +87,7 @@ namespace BlackMisc const CAltitude newAlt(m_newSituation.getCorrectedAltitude()); Q_ASSERT_X(oldAlt.getReferenceDatum() == CAltitude::MeanSeaLevel && oldAlt.getReferenceDatum() == newAlt.getReferenceDatum(), Q_FUNC_INFO, "mismatch in reference"); // otherwise no calculation is possible const CAltitude altitude((newAlt - oldAlt) - * m_simulationTimeFraction + * tf + oldAlt, oldAlt.getReferenceDatum()); @@ -102,8 +103,8 @@ namespace BlackMisc do { if (CAircraftSituation::isGfEqualAirborne(oldGroundFactor, newGroundFactor)) { newSituation.setOnGround(false); break; } - if (CAircraftSituation::isGfEqualOnGround(oldGroundFactor, newGroundFactor)) { newSituation.setOnGround(true); break; } - const double groundFactor = (newGroundFactor - oldGroundFactor) * m_simulationTimeFraction + oldGroundFactor; + if (CAircraftSituation::isGfEqualOnGround(oldGroundFactor, newGroundFactor)) { newSituation.setOnGround(true); break; } + const double groundFactor = (newGroundFactor - oldGroundFactor) * tf + oldGroundFactor; newSituation.setOnGroundFactor(groundFactor); newSituation.setOnGroundFromGroundFactorFromInterpolation(groundInterpolationFactor()); } diff --git a/src/blackmisc/simulation/interpolatorpbh.cpp b/src/blackmisc/simulation/interpolatorpbh.cpp index 901506bbe..00bb8551e 100644 --- a/src/blackmisc/simulation/interpolatorpbh.cpp +++ b/src/blackmisc/simulation/interpolatorpbh.cpp @@ -32,9 +32,12 @@ namespace BlackMisc if (CBuildConfig::isLocalDeveloperDebugBuild()) { - BLACK_VERIFY_X(isValidTimeFraction(timeFraction0to1), Q_FUNC_INFO, "0..1 fraction needed"); + BLACK_VERIFY_X(isAcceptableTimeFraction(timeFraction0to1), Q_FUNC_INFO, "0..1 fraction needed"); } + //! make sure to not end up we extrapolation + if (timeFraction0to1 >= 1.0) { return begin + CAngle(deltaDeg, CAngleUnit::deg()); } + if (timeFraction0to1 <= 0.0) { return begin; } return begin + CAngle(timeFraction0to1 * deltaDeg, CAngleUnit::deg()); }