Visual Servoing Platform version 3.7.0
Loading...
Searching...
No Matches
vpRBTrackingResult.h
1/*
2 * ViSP, open source Visual Servoing Platform software.
3 * Copyright (C) 2005 - 2025 by Inria. All rights reserved.
4 *
5 * This software is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 * See the file LICENSE.txt at the root directory of this source
10 * distribution for additional information about the GNU GPL.
11 *
12 * For using ViSP with software that can not be combined with the GNU
13 * GPL, please contact Inria about acquiring a ViSP Professional
14 * Edition License.
15 *
16 * See https://visp.inria.fr for more information.
17 *
18 * This software was developed at:
19 * Inria Rennes - Bretagne Atlantique
20 * Campus Universitaire de Beaulieu
21 * 35042 Rennes Cedex
22 * France
23 *
24 * If you have questions regarding the use of this file, please contact
25 * Inria at visp@inria.fr
26 *
27 * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
28 * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
29 */
30
35#ifndef VP_RB_TRACKING_RESULT_H
36#define VP_RB_TRACKING_RESULT_H
37
38#include <visp3/core/vpConfig.h>
39
40
41#include <vector>
42#include <visp3/core/vpColVector.h>
43#include <visp3/core/vpHomogeneousMatrix.h>
44
45#include <visp3/rbt/vpRBTrackingTimings.h>
46#include <visp3/rbt/vpRBFeatureTracker.h>
47
48#if defined(VISP_HAVE_NLOHMANN_JSON)
49#include VISP_NLOHMANN_JSON(json.hpp)
50#endif
51
61 class VISP_EXPORT vpRBFeatureResult
62{
63
64public:
65 vpRBFeatureResult() = default;
66 void onIter(unsigned int iter, unsigned int maxIters, vpRBFeatureTracker &tracker)
67 {
68 m_numFeatures.push_back(tracker.getNumFeatures());
69 double w = tracker.getVVSTrackerWeight(static_cast<double>(iter) / static_cast<double>(maxIters));
70 if (!vpMath::isFinite(w)) {
71 w = 0.0;
72 }
73 m_overallWeight.push_back(w);
74 m_error.push_back(tracker.getWeightedError());
75 m_JTJ.push_back(tracker.getLTL());
76 m_JTR.push_back(tracker.getLTR());
77 }
78
79 std::vector<unsigned int> getNumFeatures() const { return m_numFeatures; }
80 std::vector<double> getWeight() const { return m_overallWeight; }
81
82 std::vector<vpColVector> getErrors() const { return m_error; }
83 std::vector<vpMatrix> getJTJs() const { return m_JTJ; }
84 std::vector<vpColVector> getJTRs() const { return m_JTR; }
85
86
87#ifdef VISP_HAVE_NLOHMANN_JSON
88 inline friend void from_json(const nlohmann::json &j, vpRBFeatureResult &result);
89 inline friend void to_json(nlohmann::json &j, const vpRBFeatureResult &result);
90#endif
91
92private:
93 std::vector<unsigned int> m_numFeatures;
94 std::vector<double> m_overallWeight;
95
96 std::vector<vpColVector> m_error;
97 std::vector<vpMatrix> m_JTJ;
98 std::vector<vpColVector> m_JTR;
99};
100
101
102enum vpRBTrackingStoppingReason
103{
104 MAX_ITERS = 0, // Reached maximum number of iterations
105 CONVERGENCE_CRITERION = 1,
106 OBJECT_NOT_IN_IMAGE = 2,
107 NOT_ENOUGH_FEATURES = 3,
108 EXCEPTION = 4,
109 INVALID_REASON = 5
110};
111
112
121class VISP_EXPORT vpRBTrackingResult
122{
123public:
124
125 vpRBTrackingResult() : m_odometryMetric(0.0), m_odometryThreshold(0.0)
126 {
127 m_odometryMotion = vpHomogeneousMatrix();
128 }
129
130 unsigned int getNumIterations() const { return static_cast<unsigned int>(m_cMos.size()); }
131 const std::vector<vpHomogeneousMatrix> &getPoses() const { return m_cMos; }
132 vpHomogeneousMatrix getPoseBeforeTracking() const { return m_cMoBeforeTracking; }
133
134 const std::vector<vpColVector> &getVelocities() const { return m_velocities; }
135 const std::vector<double> &getConvergenceMetricValues() const { return m_convergenceMetric; }
136
137 vpRBTrackingTimings &timer() { return m_timings; }
138
139 vpRBTrackingStoppingReason getStoppingReason() const { return m_stopReason; }
140 void setStoppingReason(vpRBTrackingStoppingReason reason) { m_stopReason = reason; }
141
142 vpHomogeneousMatrix getOdometryMotion() { return m_odometryMotion; }
143
144 vpHomogeneousMatrix getPoseBeforeOdometry() { return m_cMoBeforeOdometry; }
145 vpHomogeneousMatrix getPoseAfterOdometry() { return m_cMoAfterOdometry; }
146
147 void setOdometryMotion(const vpHomogeneousMatrix &cMo_before, const vpHomogeneousMatrix &cMcp, const vpHomogeneousMatrix &cMo_after)
148 {
149 m_odometryMotion = cMcp;
150 m_cMoBeforeOdometry = cMo_before;
151 m_cMoAfterOdometry = cMo_after;
152 }
153
154 void setOdometryMetricAndThreshold(const double metricValue, const double metricThreshold)
155 {
156 m_odometryMetric = metricValue;
157 m_odometryThreshold = metricThreshold;
158 }
159
161 {
162 m_cMoBeforeTracking = cMo;
163 }
164
165 std::vector<vpRBFeatureResult> getFeatureData() const { return m_featureData; }
166
167
168 inline void onEndIter(const vpHomogeneousMatrix &cMo, const vpColVector &v, const double convergenceMetric, const vpMatrix &JTJ, const vpColVector &JTR, double mu)
169 {
170 m_cMos.push_back(cMo);
171 m_velocities.push_back(v);
172 m_convergenceMetric.push_back(convergenceMetric);
173 m_JTJ.push_back(JTJ);
174 m_JTR.push_back(JTR);
175 m_mus.push_back(mu);
176
177 }
178
179 inline void logFeatures(unsigned int iter, unsigned int maxIters, const std::vector<std::shared_ptr<vpRBFeatureTracker>> &features)
180 {
181 if (m_featureData.size() == 0) {
182 m_featureData.resize(features.size());
183 }
184 else if (m_featureData.size() != features.size()) {
185 throw vpException(vpException::dimensionError, "Wrong number of features were logged");
186 }
187
188 for (unsigned int i = 0; i < features.size(); ++i) {
189 m_featureData[i].onIter(iter, maxIters, *features[i]);
190 }
191 }
192
193#ifdef VISP_HAVE_NLOHMANN_JSON
194 void saveToFile(const std::string &path) const;
195 static vpRBTrackingResult readFromJsonFile(const std::string &path);
196 inline friend void from_json(const nlohmann::json &j, vpRBTrackingResult &result);
197 inline friend void to_json(nlohmann::json &j, const vpRBTrackingResult &result);
198#endif
199
200private:
201 vpRBTrackingStoppingReason m_stopReason;
202 vpRBTrackingTimings m_timings;
203 std::vector<vpHomogeneousMatrix> m_cMos;
204 vpHomogeneousMatrix m_cMoBeforeTracking;
205
206 std::vector<vpColVector> m_velocities;
207 std::vector<double> m_convergenceMetric;
208 std::vector<double> m_mus;
209 std::vector<vpMatrix> m_JTJ;
210 std::vector<vpColVector> m_JTR;
211
212 vpHomogeneousMatrix m_odometryMotion;
213 vpHomogeneousMatrix m_cMoBeforeOdometry, m_cMoAfterOdometry;
214
215 double m_odometryMetric, m_odometryThreshold;
216 std::vector<vpRBFeatureResult> m_featureData;
217};
218
219
220#ifdef VISP_HAVE_NLOHMANN_JSON
221
222#if defined(__clang__)
223// Mute warning : declaration requires an exit-time destructor [-Wexit-time-destructors]
224// message : expanded from macro 'NLOHMANN_JSON_SERIALIZE_ENUM'
225# pragma clang diagnostic push
226# pragma clang diagnostic ignored "-Wexit-time-destructors"
227#endif
228
229NLOHMANN_JSON_SERIALIZE_ENUM(vpRBTrackingStoppingReason, {
230 {vpRBTrackingStoppingReason::INVALID_REASON, nullptr},
231 {vpRBTrackingStoppingReason::MAX_ITERS, "maxIterations"},
232 {vpRBTrackingStoppingReason::CONVERGENCE_CRITERION, "converged"},
233 {vpRBTrackingStoppingReason::OBJECT_NOT_IN_IMAGE, "objectNotInImage"},
234 {vpRBTrackingStoppingReason::NOT_ENOUGH_FEATURES, "notEnoughFeatures"},
235 {vpRBTrackingStoppingReason::EXCEPTION, "exception"}
236});
237
238#if defined(__clang__)
239# pragma clang diagnostic pop
240#endif
241
242inline void from_json(const nlohmann::json &j, vpRBFeatureResult &result)
243{
244 result.m_numFeatures = j.at("numFeatures").get<std::vector<unsigned int>>();
245 result.m_overallWeight = j.at("weight").get<std::vector<double>>();
246 result.m_error = j.at("error");
247 result.m_JTJ = j.at("JTJ");
248 result.m_JTR = j.at("JTR");
249}
250inline void to_json(nlohmann::json &j, const vpRBFeatureResult &result)
251{
252 j["numFeatures"] = result.m_numFeatures;
253 j["weight"] = result.m_overallWeight;
254 j["error"] = result.m_error;
255 j["JTJ"] = result.m_JTJ;
256 j["JTR"] = result.m_JTR;
257}
258
259inline void from_json(const nlohmann::json &j, vpRBTrackingResult &result)
260{
261 result.m_stopReason = j.at("stopReason");
262 result.m_timings = j.at("timings");
263 result.m_cMos = j.at("cMos");
264 result.m_cMoBeforeTracking = j.at("cMoBeforeTracking");
265
266 result.m_velocities = j.at("velocities");
267 result.m_mus = j.at("mus").get<std::vector<double>>();
268 result.m_JTJ = j.at("JTJ");
269 result.m_JTR = j.at("JTR");
270
271 result.m_convergenceMetric = j.at("convergenceMetric").get<std::vector<double>>();
272 result.m_odometryMotion = j.at("odometryDisplacement");
273 result.m_cMoBeforeOdometry = j.at("cMoBeforeOdometry");
274 result.m_cMoAfterOdometry = j.at("cMoAfterOdometry");
275
276
277 result.m_odometryMetric = j.at("odometryMetric");
278 result.m_odometryThreshold = j.at("odometryThreshold");
279
280 result.m_featureData = j.at("features");
281}
282inline void to_json(nlohmann::json &j, const vpRBTrackingResult &result)
283{
284 j["stopReason"] = result.m_stopReason;
285 j["timings"] = result.m_timings;
286 j["cMos"] = result.m_cMos;
287 j["cMoBeforeTracking"] = result.m_cMoBeforeTracking;
288 j["velocities"] = result.m_velocities;
289 j["mus"] = result.m_mus;
290 j["JTJ"] = result.m_JTJ;
291 j["JTR"] = result.m_JTR;
292
293 j["convergenceMetric"] = result.m_convergenceMetric;
294 j["odometryDisplacement"] = result.m_odometryMotion;
295 j["cMoBeforeOdometry"] = result.m_cMoBeforeOdometry;
296 j["cMoAfterOdometry"] = result.m_cMoAfterOdometry;
297 j["odometryMetric"] = result.m_odometryMetric;
298 j["odometryThreshold"] = result.m_odometryThreshold;
299
300 j["features"] = result.m_featureData;
301}
302
303#endif
304
305
306END_VISP_NAMESPACE
307
308#endif
Implementation of column vector and the associated operations.
error that can be emitted by ViSP classes.
Definition vpException.h:60
@ dimensionError
Bad dimension.
Definition vpException.h:71
Implementation of an homogeneous matrix and operations on such kind of matrices.
static bool isFinite(double value)
Definition vpMath.cpp:198
Implementation of a matrix and operations on matrices.
Definition vpMatrix.h:175
std::vector< double > getWeight() const
friend void to_json(nlohmann::json &j, const vpRBFeatureResult &result)
std::vector< unsigned int > getNumFeatures() const
friend void from_json(const nlohmann::json &j, vpRBFeatureResult &result)
std::vector< vpColVector > getErrors() const
void onIter(unsigned int iter, unsigned int maxIters, vpRBFeatureTracker &tracker)
std::vector< vpMatrix > getJTJs() const
vpRBFeatureResult()=default
std::vector< vpColVector > getJTRs() const
A base class for all features that can be used and tracked in the vpRBTracker.
friend void from_json(const nlohmann::json &j, vpRBTrackingResult &result)
void setOdometryMetricAndThreshold(const double metricValue, const double metricThreshold)
void setStoppingReason(vpRBTrackingStoppingReason reason)
vpRBTrackingStoppingReason getStoppingReason() const
void setOdometryMotion(const vpHomogeneousMatrix &cMo_before, const vpHomogeneousMatrix &cMcp, const vpHomogeneousMatrix &cMo_after)
vpRBTrackingTimings & timer()
vpHomogeneousMatrix getOdometryMotion()
void onEndIter(const vpHomogeneousMatrix &cMo, const vpColVector &v, const double convergenceMetric, const vpMatrix &JTJ, const vpColVector &JTR, double mu)
friend void to_json(nlohmann::json &j, const vpRBTrackingResult &result)
vpHomogeneousMatrix getPoseBeforeOdometry()
std::vector< vpRBFeatureResult > getFeatureData() const
vpHomogeneousMatrix getPoseAfterOdometry()
void beforeIter(const vpHomogeneousMatrix &cMo)
const std::vector< vpHomogeneousMatrix > & getPoses() const
const std::vector< vpColVector > & getVelocities() const
const std::vector< double > & getConvergenceMetricValues() const
unsigned int getNumIterations() const
void logFeatures(unsigned int iter, unsigned int maxIters, const std::vector< std::shared_ptr< vpRBFeatureTracker > > &features)
vpHomogeneousMatrix getPoseBeforeTracking() const