Skip to content

Commit

Permalink
Merge pull request lagadic#1324 from SamFlt/feat_json_mbt_improvements
Browse files Browse the repository at this point in the history
Feat: MBT JSON improvements
  • Loading branch information
fspindle authored Feb 4, 2024
2 parents 63bfb48 + 8d8a92f commit b370a00
Show file tree
Hide file tree
Showing 9 changed files with 120 additions and 20 deletions.
24 changes: 24 additions & 0 deletions doc/tutorial/tracking/tutorial-tracking-mb-generic-json.dox
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ Let us first examine the global settings (located at the root of the JSON struct
\endcode

If they are defined globally, they will take precedence over the values defined per tracker.
Some settings such as the "vvs" options, are only defined globally

<table>
<tr><th colspan="2">Key</th><th>Type</th><th>Description</th><th>Optional</th></tr>
Expand Down Expand Up @@ -98,6 +99,29 @@ If they are defined globally, they will take precedence over the values defined
<td>Whether to use ogre for visibility testing. OGRE must be installed, otherwise ignored. See vpMbGenericTracker::setOgreVisibilityTest()</td>
<td>Yes</td>
</tr>
<tr><th colspan="5">vvs (optional)</th></tr>
<tr>
<td>lambda</td>
<td>float</td>
<td>Virtual visual servoing gain
</td>
<td>vpMbGenericTracker::setLambda()</td>
<td>Yes</td>
</tr>
<tr>
<td>maxIter</td>
<td>integer > 0</td>
<td>Number of iterations for virtual visual servoing</td>
<td>vpMbGenericTracker::setMaxIter()</td>
<td>Yes</td>
</tr>
<tr>
<td>initialMu</td>
<td>float</td>
<td>Initial Mu for levenberg marquardt optimization</td>
<td>vpMbGenericTracker::setInitialMu(</td>
<td>Yes</td>
</tr>
</table>

\subsection json-per-tracker-settings Individual camera tracker settings
Expand Down
4 changes: 3 additions & 1 deletion modules/tracker/mbt/include/visp3/mbt/vpMbGenericTracker.h
Original file line number Diff line number Diff line change
Expand Up @@ -175,7 +175,8 @@
* "range": 4,
* "sampleStep": 10.0,
* "strip": 2,
* "threshold": 1500.0
* "thresholdType": "normalized",
* "threshold": 20.0
* },
* "lod": {
* "minLineLengthThresholdGeneral": 50.0,
Expand Down Expand Up @@ -1022,6 +1023,7 @@ inline void from_json(const nlohmann::json &j, vpMbGenericTracker::TrackerWrappe
//Edge tracker settings
if (t.m_trackerType & vpMbGenericTracker::EDGE_TRACKER) {
from_json(j.at("edge"), t.me);
t.setMovingEdge(t.me);
}
//KLT tracker settings
#if defined(VISP_HAVE_MODULE_KLT) && defined(VISP_HAVE_OPENCV) && defined(HAVE_OPENCV_IMGPROC) && defined(HAVE_OPENCV_VIDEO)
Expand Down
15 changes: 15 additions & 0 deletions modules/tracker/mbt/src/vpMbGenericTracker.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3019,6 +3019,15 @@ void vpMbGenericTracker::loadConfigFileJSON(const std::string &settingsFile, boo
setOgreVisibilityTest(visJson.value("ogre", useOgre));
setScanLineVisibilityTest(visJson.value("scanline", useScanLine));
}

// VVS global settings
if (settings.contains("vvs")) {
const json vvsJson = settings["vvs"];
setLambda(vvsJson.value("lambda", this->m_lambda));
setMaxIter(vvsJson.value("maxIter", this->m_maxIter));
setInitialMu(vvsJson.value("initialMu", this->m_initialMu));
}

//If a 3D model is defined, load it
if (settings.contains("model")) {
loadModel(settings.at("model").get<std::string>(), verbose);
Expand Down Expand Up @@ -3047,6 +3056,12 @@ void vpMbGenericTracker::saveConfigFile(const std::string &settingsFile) const
}
}
j["trackers"] = trackers;
j["vvs"] = json {
{"lambda", m_lambda},
{"maxIter", m_maxIter},
{"initialMu", m_initialMu}
};

std::ofstream f(settingsFile);
if (f.good()) {
const unsigned indentLevel = 4;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,17 @@ vpMbGenericTracker baseTrackerConstructor()

t.setAngleAppear(vpMath::rad(60));
t.setAngleDisappear(vpMath::rad(90));
vpMe me;
me.setSampleStep(2.0);
me.setMaskSize(7);
me.setMaskNumber(160);
me.setRange(8);
me.setLikelihoodThresholdType(vpMe::NORMALIZED_THRESHOLD);
me.setThreshold(20);
me.setMu1(0.2);
me.setMu2(0.3);
me.setSampleStep(4);
t.setMovingEdge(me);
return t;
}

Expand Down Expand Up @@ -103,7 +114,6 @@ void compareNamesAndTypes(const vpMbGenericTracker &t1, const vpMbGenericTracker
void compareCameraParameters(const vpMbGenericTracker &t1, const vpMbGenericTracker &t2)
{
std::map<std::string, vpCameraParameters> c1, c2;
vpCameraParameters c;
t1.getCameraParameters(c1);
t2.getCameraParameters(c2);
REQUIRE(c1 == c2);
Expand Down Expand Up @@ -185,6 +195,8 @@ SCENARIO("MBT JSON Serialization", "[json]")
&vpMe::getMaskNumber, "Mask number should be equal",
&vpMe::getMaskSign, "Mask sign should be equal",
&vpMe::getMinSampleStep, "Min sample step should be equal",
&vpMe::getSampleStep, "Min sample step should be equal",

&vpMe::getMu1, "Mu 1 should be equal",
&vpMe::getMu2, "Mu 2 should be equal",
&vpMe::getNbTotalSample, "Nb total sample should be equal",
Expand Down Expand Up @@ -245,37 +257,53 @@ SCENARIO("MBT JSON Serialization", "[json]")
);
}

THEN("VVS properties should be the same")
{
vpMbGenericTracker t2 = baseTrackerConstructor();
t2.setMaxIter(4096);
t2.setLambda(5.0);
t2.setInitialMu(5.0);

t2.loadConfigFile(jsonPath);

checkProperties(t1, t2,
&vpMbGenericTracker::getMaxIter, "VVS m iterations be the same",
&vpMbGenericTracker::getLambda, "VVS lambda should be the same",
&vpMbGenericTracker::getInitialMu, "VVS initial mu be the same"
);
}

WHEN("Modifying JSON file/Using a custom JSON file")
{
THEN("Removing version from file generates an error on load")
{
modifyJson([](json &j) -> void {
j.erase("version");
});
});
REQUIRE_THROWS(t1.loadConfigFile(jsonPath));
}

THEN("Using an unsupported version generates an error on load")
{
modifyJson([](json &j) -> void {
j["version"] = "0.0.0";
});
});
REQUIRE_THROWS(t1.loadConfigFile(jsonPath));
}

THEN("Using an undefined reference camera generates an error")
{
modifyJson([](json &j) -> void {
j["referenceCameraName"] = "C3";
});
});
REQUIRE_THROWS(t1.loadConfigFile(jsonPath));
}

THEN("Not defining a transformation matrix for the reference camera is valid")
{
modifyJson([&t1](json &j) -> void {
j["trackers"][t1.getReferenceCameraName()].erase("camTref");
});
});
REQUIRE_NOTHROW(t1.loadConfigFile(jsonPath));
}

Expand All @@ -284,7 +312,7 @@ SCENARIO("MBT JSON Serialization", "[json]")
modifyJson([&t1](json &j) -> void {
std::string otherCamName = t1.getReferenceCameraName() == "C1" ? "C2" : "C1";
j["trackers"][otherCamName].erase("camTref");
});
});
REQUIRE_THROWS(t1.loadConfigFile(jsonPath));
}

Expand All @@ -301,7 +329,7 @@ SCENARIO("MBT JSON Serialization", "[json]")
for (const auto &c : t1.getCameraNames()) {
j["trackers"][c].erase("clipping");
}
});
});
REQUIRE_NOTHROW(t2.loadConfigFile(jsonPath, false));
REQUIRE(t2.getClipping() == clipping);
REQUIRE(t2.getNearClippingDistance() == clipping_near);
Expand All @@ -323,7 +351,7 @@ SCENARIO("MBT JSON Serialization", "[json]")
for (const auto &c : t1.getCameraNames()) {
j["trackers"][c]["clipping"].erase("near");
}
});
});
t2.loadConfigFile(jsonPath);
REQUIRE(t2.getNearClippingDistance() == clipping_near);
REQUIRE(t2.getFarClippingDistance() == t1.getFarClippingDistance());
Expand All @@ -335,7 +363,7 @@ SCENARIO("MBT JSON Serialization", "[json]")
for (const auto &c : t1.getCameraNames()) {
j["trackers"][c]["clipping"].erase("far");
}
});
});
t2.loadConfigFile(jsonPath);
REQUIRE(t2.getNearClippingDistance() == t1.getNearClippingDistance());
REQUIRE(t2.getFarClippingDistance() == clipping_far);
Expand All @@ -347,7 +375,7 @@ SCENARIO("MBT JSON Serialization", "[json]")
for (const auto &c : t1.getCameraNames()) {
j["trackers"][c]["clipping"].erase("flags");
}
});
});
t2.loadConfigFile(jsonPath);
REQUIRE(t2.getNearClippingDistance() == t1.getNearClippingDistance());
REQUIRE(t2.getFarClippingDistance() == t1.getFarClippingDistance());
Expand All @@ -358,7 +386,7 @@ SCENARIO("MBT JSON Serialization", "[json]")
}
}
}
int main(int argc, char *argv [])
int main(int argc, char *argv[])
{
Catch::Session session; // There must be exactly one instance
session.applyCommandLine(argc, argv);
Expand Down
13 changes: 9 additions & 4 deletions modules/tracker/me/include/visp3/me/vpMe.h
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@
* \code{.unparsed}
* $ cat me.json
* {"maskSign":0,"maskSize":5,"minSampleStep":4.0,"mu":[0.5,0.5],"nMask":180,"ntotalSample":0,"pointsToTrack":200,
* "range":5,"sampleStep":10.0,"strip":2,"threshold":20.0,"thresholdMarginRatio":-1.0,"minThreshold":-1.0,"thresholdType":1}
* "range":5,"sampleStep":10.0,"strip":2,"threshold":20.0,"thresholdMarginRatio":-1.0,"minThreshold":-1.0,"thresholdType":"normalized"}
* \endcode
*/
class VISP_EXPORT vpMe
Expand Down Expand Up @@ -531,7 +531,7 @@ class VISP_EXPORT vpMe
* @brief Retrieve a vpMe object from a JSON representation
*
* JSON content (key: type):
* - thresholdType: int, vpMe::getLikelihoodThresholdType()
* - thresholdType: either "old" or "normalized", vpMe::getLikelihoodThresholdType()
* - threshold: double, vpMe::setThreshold()
* - thresholdMarginRatio: double, vpMe::setThresholdMarginRatio()
* - minThreshold: double, vpMe::setMinThreshold()
Expand Down Expand Up @@ -564,7 +564,7 @@ class VISP_EXPORT vpMe
* "range": 7,
* "sampleStep": 4.0,
* "strip": 2,
* "thresholdType": 1,
* "thresholdType": "normalized",
* "threshold": 20.0,
* "thresholdMarginRatio": 0.75,
* "minThreshold": 20.0,
Expand All @@ -580,6 +580,11 @@ class VISP_EXPORT vpMe
#ifdef VISP_HAVE_NLOHMANN_JSON
#include <nlohmann/json.hpp>

NLOHMANN_JSON_SERIALIZE_ENUM(vpMe::vpLikelihoodThresholdType, {
{vpMe::vpLikelihoodThresholdType::OLD_THRESHOLD, "old"},
{vpMe::vpLikelihoodThresholdType::NORMALIZED_THRESHOLD, "normalized"}
});

inline void to_json(nlohmann::json &j, const vpMe &me)
{
j = {
Expand Down Expand Up @@ -616,7 +621,7 @@ inline void from_json(const nlohmann::json &j, vpMe &me)
me.setMu2(mus[1]);
}
me.setMinSampleStep(j.value("minSampleStep", me.getMinSampleStep()));

me.setSampleStep(j.value("sampleStep", me.getSampleStep()));
me.setRange(j.value("range", me.getRange()));
me.setNbTotalSample(j.value("ntotalSample", me.getNbTotalSample()));
me.setPointsToTrack(j.value("pointsToTrack", me.getPointsToTrack()));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@
"range": 7,
"sampleStep": 4.0,
"strip": 2,
"thresholdType": "old",
"threshold": 5000.0
},
"klt": {
Expand Down Expand Up @@ -163,5 +164,10 @@
}
}
},
"vvs" :{
"lambda": 1.0,
"maxIter": 30,
"initialMu": 0.01
},
"version": "1.0"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@
"range": 7,
"sampleStep": 4.0,
"strip": 2,
"thresholdType": "old",
"threshold": 5000.0
},
"klt": {
Expand Down Expand Up @@ -162,5 +163,10 @@
}
}
},
"vvs" :{
"lambda": 1.0,
"maxIter": 30,
"initialMu": 0.01
},
"version": "1.0"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@
"range": 7,
"sampleStep": 4.0,
"strip": 2,
"thresholdType": "old",
"threshold": 5000.0
},
//! [Edge]
Expand Down Expand Up @@ -178,5 +179,12 @@
}
}
},
//! [VVS]
"vvs" :{
"lambda": 1.0,
"maxIter": 30,
"initialMu": 0.01
},
//! [VVS]
"version": "1.0"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@
"range": 7,
"sampleStep": 4.0,
"strip": 2,
"thresholdType": "old",
"threshold": 5000.0
},
"klt": {
Expand Down Expand Up @@ -86,5 +87,10 @@
}
}
},
"vvs" :{
"lambda": 1.0,
"maxIter": 30,
"initialMu": 0.01
},
"version": "1.0"
}
}

0 comments on commit b370a00

Please sign in to comment.