42 [[nodiscard]]
static std::string
type()
49 [[nodiscard]] std::string
getType()
const override {
return type(); }
65 desc.emplace_back(
"Solution Type");
66 desc.emplace_back(
"Number satellites");
67 desc.emplace_back(
"Number pseudorange observables");
68 desc.emplace_back(
"Number carrier observables");
69 desc.emplace_back(
"Number doppler observables");
70 desc.emplace_back(
"Number pseudorange observables (unique per satellite)");
71 desc.emplace_back(
"Number carrier observables (unique per satellite)");
72 desc.emplace_back(
"Number doppler observables (unique per satellite)");
73 desc.emplace_back(
"Ambiguity Resolution Failure");
74 desc.emplace_back(
"Ambiguity Critical Value µ ∈ (0, 1] (R1/R2 ≤ µ)");
75 desc.emplace_back(
"Number of Ambiguities fixed");
76 desc.emplace_back(
"NIS Triggered (Initial)");
77 desc.emplace_back(
"NIS value (Initial)");
78 desc.emplace_back(
"NIS r2 upper boundary (Initial)");
79 desc.emplace_back(
"NIS removed observations");
80 desc.emplace_back(
"NIS Triggered (Final)");
81 desc.emplace_back(
"NIS value (Final)");
82 desc.emplace_back(
"NIS r2 upper boundary (Final)");
83 desc.emplace_back(
"Distance Rover-Base [m]");
99 [[nodiscard]] std::optional<double>
getValueAt(
size_t idx)
const override
106 return static_cast<double>(
solType);
165 std::vector<std::string> descriptors;
170 descriptors.push_back(fmt::format(
"AmbDD {} [cycles]", ambDD.satSigId));
171 descriptors.push_back(fmt::format(
"AmbDD StDev {} [cycles]", ambDD.satSigId));
176 if (std::holds_alternative<RTK::Meas::PsrDD>(key)) { descriptors.push_back(fmt::format(
"Innovation {} [m]", key)); }
177 else if (std::holds_alternative<RTK::Meas::CarrierDD>(key)) { descriptors.push_back(fmt::format(
"Innovation {} [m]", key)); }
178 else if (std::holds_alternative<RTK::Meas::DopplerDD>(key)) { descriptors.push_back(fmt::format(
"Innovation {} [m/s]", key)); }
179 else if (std::holds_alternative<RTK::States::AmbiguityDD>(key)) { descriptors.push_back(fmt::format(
"Innovation {} [cyc]", key)); }
183 descriptors.push_back(fmt::format(
"{} Elevation [deg]", satId));
184 descriptors.push_back(fmt::format(
"{} Azimuth [deg]", satId));
192 [[nodiscard]] std::optional<double>
getDynamicDataAt(
const std::string& descriptor)
const override
196 if (descriptor == fmt::format(
"AmbDD {} [cycles]", ambDD.satSigId)) {
return ambDD.value.value; }
197 if (descriptor == fmt::format(
"AmbDD StDev {} [cycles]", ambDD.satSigId)) {
return ambDD.value.stdDev; }
201 if (descriptor.starts_with(fmt::format(
"Innovation {}", key))) {
return measInnovation(key); }
205 if (descriptor == fmt::format(
"{} Elevation [deg]", satId)) {
return rad2deg(
satData.satElevation); }
206 if (descriptor == fmt::format(
"{} Azimuth [deg]", satId)) {
return rad2deg(
satData.satAzimuth); }
212 [[nodiscard]] std::vector<std::pair<std::string, double>>
getDynamicData()
const override
214 std::vector<std::pair<std::string, double>> dynData;
218 dynData.emplace_back(fmt::format(
"AmbDD {} [cycles]", ambDD.satSigId), ambDD.value.value);
219 dynData.emplace_back(fmt::format(
"AmbDD StDev {} [cycles]", ambDD.satSigId), ambDD.value.stdDev);
223 if (std::holds_alternative<RTK::Meas::PsrDD>(key)) { dynData.emplace_back(fmt::format(
"Innovation {} [m]", key),
measInnovation(key)); }
224 else if (std::holds_alternative<RTK::Meas::CarrierDD>(key)) { dynData.emplace_back(fmt::format(
"Innovation {} [m]", key),
measInnovation(key)); }
225 else if (std::holds_alternative<RTK::Meas::DopplerDD>(key)) { dynData.emplace_back(fmt::format(
"Innovation {} [m/s]", key),
measInnovation(key)); }
226 else if (std::holds_alternative<RTK::States::AmbiguityDD>(key)) { dynData.emplace_back(fmt::format(
"Innovation {} [cyc]", key),
measInnovation(key)); }
230 dynData.emplace_back(fmt::format(
"{} Elevation [deg]", satId),
rad2deg(
satData.satElevation));
231 dynData.emplace_back(fmt::format(
"{} Azimuth [deg]", satId),
rad2deg(
satData.satAzimuth));
242 void guiTooltip(
bool detailView,
bool firstOpen,
const char* displayName,
const char*
id,
int* rootWindow)
const override;
245 [[nodiscard]]
bool hasTooltip()
const override {
return true; }
367 std::optional<KeyedKalmanFilter<double, RTK::States::StateKeyType, RTK::Meas::MeasKeyTypes>::NISResult>
nisResultInitial;
369 std::optional<KeyedKalmanFilter<double, RTK::States::StateKeyType, RTK::Meas::MeasKeyTypes>::NISResult>
nisResultFinal;
397 std::vector<std::pair<SatId, SatData>>
satData;
417 bool colorCycleSlips,
418 bool colorPivotChanges,
419 const char*
id)
const;
428#ifndef DOXYGEN_IGNORE
432struct fmt::formatter<
NAV::RtkSolution::SolutionType> : fmt::formatter<const char*>
438 template<
typename FormatContext>
444 return fmt::formatter<const char*>::format(
"None", ctx);
446 return fmt::formatter<const char*>::format(
"SPP", ctx);
448 return fmt::formatter<const char*>::format(
"Predicted", ctx);
450 return fmt::formatter<const char*>::format(
"Float", ctx);
452 return fmt::formatter<const char*>::format(
"Fixed", ctx);
460struct fmt::formatter<
NAV::RtkSolution::Outlier::Type> : fmt::formatter<const char*>
466 template<
typename FormatContext>
472 return fmt::formatter<const char*>::format(
"None", ctx);
474 return fmt::formatter<const char*>::format(
"NIS check", ctx);
482struct fmt::formatter<
NAV::RtkSolution::PivotChange> : fmt::formatter<std::string>
488 template<
typename FormatContext>
489 auto format(
const NAV::RtkSolution::PivotChange& pivot, FormatContext& ctx)
const
494 return fmt::formatter<std::string>::format(
"Pivot change reason is unknown", ctx);
496 return fmt::formatter<std::string>::format(fmt::format(
"Pivot change [{}]: [{}] -> [{}]\n"
497 "Old pivot not observed this epoch\n"
498 "New pivot elevation {:.4}°",
503 return fmt::formatter<std::string>::format(fmt::format(
"Pivot change [{}]: [{}] -> [{}]\n"
504 "Old pivot had cycle-slip\n"
505 "Elevation {:.4}° -> {:.4}°",
511 return fmt::formatter<std::string>::format(fmt::format(
"Pivot change [{}]: [{}] -> [{}]\n"
512 "Satellite with higher elevation found\n"
513 "Elevation {:.4}° -> {:.4}°",
519 return fmt::formatter<std::string>::format(fmt::format(
"New pivot [{}][{}]\n"
525 return fmt::formatter<std::string>::format(fmt::format(
"Pivot change [{}]: [{}] -> [{}]\n"
526 "Old pivot flagged as outlier\n"
Ambiguity resolution algorithms.
#define INS_ASSERT(_EXPR)
Assert function wrapper.
Combination of different cycle-slip detection algorithms.
Keys for the RTK algorithm for use inside the KeyedMatrices.
GNSS Observation messages.
Kalman Filter with keyed states.
Position and Velocity Storage Class.
Structs identifying a unique satellite.
Values with an uncertainty (Standard Deviation)
ObservationType
Observation types.
@ Doppler
Doppler (Pseudorange rate)
@ ObservationType_COUNT
Count.
@ Pseudorange
Pseudorange.
The class is responsible for all time-related tasks.
Position and Velocity Storage Class.
static constexpr size_t GetStaticDescriptorCount()
Get the amount of descriptors.
static std::vector< std::string > parentTypes()
Returns the parent types of the data class.
static std::vector< std::string > GetStaticDataDescriptors()
Returns a vector of data descriptors.
static std::string type()
Returns the type of the data class.
std::optional< double > getValueAt(size_t idx) const override
Get the value at the index.
std::multiset< Observable > observableReceived
Observables available from receivers (only if double diff possible)
std::vector< std::string > staticDataDescriptors() const override
Returns a vector of data descriptors.
std::vector< AmbiguityDD > ambiguityDD_br
Double differenced ambiguities.
void guiTooltipSatellites(const std::map< SatelliteSystem, std::unordered_set< SatId > > &satsReceived, const char *id) const
Print a table for the satellites.
static constexpr size_t GetStaticDescriptorCount()
Get the amount of descriptors.
ObservationFilter::Filtered filtered
Signals filtered by the observation filter.
std::unordered_map< GnssObs::ObservationType, size_t > nObservations
Number of utilized observations (including pivot)
static std::vector< std::string > GetStaticDataDescriptors()
Returns a vector of data descriptors.
void guiTooltipAmbiguities(const char *id) const
Print a table for the ambiguities.
std::vector< std::pair< SatId, SatData > > satData
Extended data for each satellite.
std::unordered_map< GnssObs::ObservationType, size_t > nObservationsUniqueSatellite
Number of utilized observations (counted once for each satellite)
std::optional< double > getDynamicDataAt(const std::string &descriptor) const override
Get the value for the descriptor.
std::vector< SatSigId > newEstimatedAmbiguity
Newly estimated ambiguities.
std::string getType() const override
Returns the type of the data class.
static std::vector< std::string > parentTypes()
Returns the parent types of the data class.
std::optional< double > getValueAt(size_t idx) const override
Get the value at the index.
InsTime baseTime
Time of the base observation used.
std::optional< size_t > nAmbiguitiesFixed
Number of Ambiguities fixed.
SolutionType
Possible types of the RTK solution.
@ Predicted
Only predicted by Kalman Filter.
@ RTK_Fixed
RTK solution with fixed ambiguities to integers.
@ RTK_Float
RTK solution with floating point ambiguities.
@ None
No solution type specified.
@ SPP
Solution calculated via SPP algorithm because of missing data for RTK.
size_t nisRemovedCnt
Amount of observations removed by NIS.
void guiTooltipObservationTable(const std::multiset< RtkSolution::Observable > &observables, bool showSatCounts, bool colorPivots, bool colorNotUsed, bool colorCycleSlips, bool colorPivotChanges, const char *id) const
Print an observation table to the GUI.
std::vector< std::string > dynamicDataDescriptors() const override
Returns a vector of data descriptors for the dynamic data.
SolutionType solType
Type of th solution.
std::vector< std::pair< std::string, double > > getDynamicData() const override
Returns a vector of data descriptors and values for the dynamic data.
std::multiset< Observable > observableFiltered
Observables available from receivers, but filtered by GUI settings.
std::multiset< Observable > observableUsed
Observables used for the final solution.
std::multiset< Observable > pivots
List of pivot satellites.
KeyedVectorXd< RTK::Meas::MeasKeyTypes > measInnovation
𝐳 Measurement vector
std::vector< std::pair< CycleSlipDetector::Result, std::string > > cycleSlipDetectorResult
Cycle slip detector results and name of the receiver.
std::optional< KeyedKalmanFilter< double, RTK::States::StateKeyType, RTK::Meas::MeasKeyTypes >::NISResult > nisResultFinal
Normalized Innovation Squared (NIS) test result (last NIS iteration)
std::unordered_map< std::pair< Code, GnssObs::ObservationType >, PivotChange > changedPivotSatellites
List of pivot satellite changes.
std::vector< Outlier > outliers
List of found outliers.
static std::string type()
Returns the type of the data class.
AmbiguityResolutionFailure ambiguityResolutionFailure
Ambiguity resolution failure.
size_t staticDescriptorCount() const override
Get the amount of descriptors.
bool hasTooltip() const override
Return whether this data has a tooltip.
std::optional< KeyedKalmanFilter< double, RTK::States::StateKeyType, RTK::Meas::MeasKeyTypes >::NISResult > nisResultInitial
Normalized Innovation Squared (NIS) test result (before removing anything)
size_t nSatellites
Amount of satellites used.
double distanceBaseRover
Distance of Rover to base [m].
void guiTooltip(bool detailView, bool firstOpen, const char *displayName, const char *id, int *rootWindow) const override
Shows a GUI tooltip to look into details of the observation.
double ambiguityCriticalValueRatio
Ambiguity Critical Value µ ∈ (0, 1] (R1/R2 ≤ µ)
KeyedVectorX< double, RowKeyType > KeyedVectorXd
Dynamic size KeyedVector with double types.
AmbiguityResolutionFailure
Possible failures.
constexpr auto rad2deg(const T &rad)
Convert Radians to Degree.
Ambiguity double differences.
UncertainValue< double > value
Value.
SatSigId satSigId
Satellite Signal id.
SatSigId pivotSatSigId
Pivot satellite Signal Id.
SatSigId satSigId
Satellite Signal Id.
GnssObs::ObservationType obsType
Observation Type.
bool operator<(const Observable &rhs) const
Less than comparison (needed for map)
Observable(SatSigId satSigId, GnssObs::ObservationType obsType)
Constructor.
GnssObs::ObservationType obsType
Observation Type.
Outlier(const Type &type, const SatSigId &satSigId, const GnssObs::ObservationType &obsType)
Constructor.
@ NIS
Normalized Innovation Squared (NIS)
SatSigId satSigId
Satellite Signal Id.
Pivot Change information.
SatSigId newPivotSat
New SatSig identifier.
double oldPivotElevation
Old Satellite elevation [rad].
GnssObs::ObservationType obsType
Observation type.
Reason
Possible reasons for a pivot change.
@ PivotNotObservedInEpoch
Old pivot satellite was not observed this epoch.
@ PivotCycleSlip
The pivot satellite had a cycle-slip.
@ PivotOutlier
Old pivot satellite was flagged as outlier.
@ None
No reason selected yet.
@ HigherElevationFound
A satellite with higher elevation was observed.
@ NewCode
Code was not observed before.
double newPivotElevation
New Satellite elevation [rad].
SatSigId oldPivotSat
Old SatSig identifier.
double satElevation
Satellite Elevation [rad].
double satAzimuth
Satellite Azimuth [rad].
Identifies a satellite signal (satellite frequency and number)
Value with standard deviation.
Matrix which can be accessed by keys.