Visual Servoing Platform version 3.7.0
Loading...
Searching...
No Matches
vpTemplateTrackerMIForwardCompositional.cpp
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 * Description:
31 * Example of template tracking.
32 *
33 * Authors:
34 * Amaury Dame
35 * Aurelien Yol
36 */
37#include <visp3/tt_mi/vpTemplateTrackerMIForwardCompositional.h>
38
43
45{
46 ptTemplateSupp = new vpTemplateTrackerPointSuppMIInv[templateSize];
47 for (unsigned int point = 0; point < templateSize; point++) {
48 int i = ptTemplate[point].y;
49 int j = ptTemplate[point].x;
50 X1[0] = j;
51 X1[1] = i;
52 Warp->computeDenom(X1, p);
53 ptTemplate[point].dW = new double[2 * nbParam];
54 Warp->getdWdp0(i, j, ptTemplate[point].dW);
55
56 double Tij = ptTemplate[point].val;
57 int ct = static_cast<int>((Tij * (Nc - 1)) / 255.);
58 double et = (Tij * (Nc - 1)) / 255. - ct;
59 ptTemplateSupp[point].et = et;
60 ptTemplateSupp[point].ct = ct;
61 ptTemplateSupp[point].Bt = new double[4];
62 ptTemplateSupp[point].dBt = new double[4];
63 for (char it = -1; it <= 2; it++) {
64 ptTemplateSupp[point].Bt[it + 1] = vpTemplateTrackerBSpline::Bspline4(-it + et);
65 ptTemplateSupp[point].dBt[it + 1] = vpTemplateTrackerMIBSpline::dBspline4(-it + et);
66 }
67 }
68 CompoInitialised = true;
69}
71{
72 initCompo();
73
74 dW = 0;
75
76 if (blur)
80
81 int Nbpoint = 0;
82
83 double IW, dx, dy;
84 int cr, ct;
85 double er, et;
86
87 Nbpoint = 0;
88
90
91 Warp->computeCoeff(p);
92 for (unsigned int point = 0; point < templateSize; point++) {
93 int i = ptTemplate[point].y;
94 int j = ptTemplate[point].x;
95 X1[0] = j;
96 X1[1] = i;
97
98 Warp->computeDenom(X1, p);
99 Warp->warpX(X1, X2, p);
100
101 double j2 = X2[0];
102 double i2 = X2[1];
103
104 if ((i2 >= 0) && (j2 >= 0) && (i2 < I.getHeight() - 1) && (j2 < I.getWidth() - 1)) {
105 Nbpoint++;
106 if (!blur)
107 IW = I.getValue(i2, j2);
108 else
109 IW = BI.getValue(i2, j2);
110
111 dx = dIx.getValue(i2, j2) * (Nc - 1) / 255.;
112 dy = dIy.getValue(i2, j2) * (Nc - 1) / 255.;
113
114 cr = ptTemplateSupp[point].ct;
115 er = ptTemplateSupp[point].et;
116 ct = static_cast<int>((IW * (Nc - 1)) / 255.);
117 et = (static_cast<double>(IW) * (Nc - 1)) / 255. - ct;
118
119 Warp->dWarpCompo(X1, X2, p, ptTemplate[point].dW, dW);
120
121 double *tptemp = new double[nbParam];
122 for (unsigned int it = 0; it < nbParam; it++)
123 tptemp[it] = dW[0][it] * dx + dW[1][it] * dy;
124
125 vpTemplateTrackerMIBSpline::PutTotPVBspline(PrtTout, cr, er, ct, et, Nc, tptemp, nbParam, bspline);
126
127 delete[] tptemp;
128 }
129 }
130 double MI;
131 computeProba(Nbpoint);
132 computeMI(MI);
134
136
138 HLMdesireInverse = HLMdesire.inverseByLU();
139}
140
142{
143 if (!CompoInitialised) {
144 std::cout << "Compositionnal tracking not initialised.\nUse initCompo() function." << std::endl;
145 }
146 dW = 0;
147
148 if (blur) {
150 }
153
155 double MI = 0, MIprec = -1000;
156
158
160
161 double i2, j2;
162 double IW;
163 int cr, ct;
164 double er, et;
165 double dx, dy;
166
167 vpColVector dpinv(nbParam);
168 double alpha = 2.;
169
170 int i, j;
171 unsigned int iteration = 0;
172
173 double evolRMS_init = 0;
174 double evolRMS_prec = 0;
175 double evolRMS_delta;
176
177 do {
178 int Nbpoint = 0;
179 MIprec = MI;
180 MI = 0;
181
183
184 Warp->computeCoeff(p);
185
186 for (unsigned int point = 0; point < templateSize; point++) {
187 i = ptTemplate[point].y;
188 j = ptTemplate[point].x;
189 X1[0] = j;
190 X1[1] = i;
191 Warp->warpX(i, j, i2, j2, p);
192 X2[0] = j2;
193 X2[1] = i2;
194
195 Warp->computeDenom(X1, p);
196 if ((i2 >= 0) && (j2 >= 0) && (i2 < I.getHeight() - 1) && (j2 < I.getWidth() - 1)) {
197 Nbpoint++;
198 if (!blur)
199 IW = I.getValue(i2, j2);
200 else
201 IW = BI.getValue(i2, j2);
202
203 dx = dIx.getValue(i2, j2) * (Nc - 1) / 255.;
204 dy = dIy.getValue(i2, j2) * (Nc - 1) / 255.;
205
206 ct = static_cast<int>((IW * (Nc - 1)) / 255.);
207 et = (static_cast<double>(IW) * (Nc - 1)) / 255. - ct;
208 cr = ptTemplateSupp[point].ct;
209 er = ptTemplateSupp[point].et;
210
211 Warp->dWarpCompo(X1, X2, p, ptTemplate[point].dW, dW);
212
213 double *tptemp = new double[nbParam];
214 for (unsigned int it = 0; it < nbParam; it++)
215 tptemp[it] = dW[0][it] * dx + dW[1][it] * dy;
216
218 vpTemplateTrackerMIBSpline::PutTotPVBsplineNoSecond(PrtTout, cr, er, ct, et, Nc, tptemp, nbParam, bspline);
220 vpTemplateTrackerMIBSpline::PutTotPVBspline(PrtTout, cr, er, ct, et, Nc, tptemp, nbParam, bspline);
221
222 delete[] tptemp;
223 }
224 }
225 if (Nbpoint == 0) {
226 diverge = true;
227 MI = 0;
228 throw(vpTrackingException(vpTrackingException::notEnoughPointError, "No points in the template"));
229 }
230 else {
231 computeProba(Nbpoint);
232 computeMI(MI);
236
238
239 try {
240 switch (hessianComputation) {
243 break;
245 if (HLM.cond() > HLMdesire.cond())
247 else
248 dp = gain * 0.2 * HLM.inverseByLU() * G;
249 break;
250 default:
251 dp = gain * 0.2 * HLM.inverseByLU() * G;
252 break;
253 }
254 }
255 catch (const vpException &e) {
256 throw(e);
257 }
258 }
259
261 dp = -0.04 * dp;
262 // else
263 // dp = 1. * dp;
264
265 if (useBrent) {
266 alpha = 2.;
267 computeOptimalBrentGain(I, p, -MI, dp, alpha);
268 dp = alpha * dp;
269 }
270 Warp->pRondp(p, dp, p);
272
273 if (iteration == 0) {
274 evolRMS_init = evolRMS;
275 }
276
277 iteration++;
278
279 evolRMS_delta = std::fabs(evolRMS - evolRMS_prec);
280 evolRMS_prec = evolRMS;
281
282 } while ((std::fabs(MI - MIprec) > std::fabs(MI) * std::numeric_limits<double>::epsilon()) &&
283 (iteration < iterationMax) && (evolRMS_delta > std::fabs(evolRMS_init) * evolRMS_eps));
284
285 nbIteration = iteration;
286
290 }
291}
292END_VISP_NAMESPACE
Implementation of column vector and the associated operations.
error that can be emitted by ViSP classes.
Definition vpException.h:60
static void getGradXGauss2D(const vpImage< ImageType > &I, vpImage< FilterType > &dIx, const FilterType *gaussianKernel, const FilterType *gaussianDerivativeKernel, unsigned int size, const vpImage< bool > *p_mask=nullptr)
static void filter(const vpImage< ImageType > &I, vpImage< FilterType > &If, const vpArray2D< FilterType > &M, bool convolve=false, const vpImage< bool > *p_mask=nullptr)
static void getGradYGauss2D(const vpImage< ImageType > &I, vpImage< FilterType > &dIy, const FilterType *gaussianKernel, const FilterType *gaussianDerivativeKernel, unsigned int size, const vpImage< bool > *p_mask=nullptr)
Definition of the vpImage class member functions.
Definition vpImage.h:131
static void computeHLM(const vpMatrix &H, const double &alpha, vpMatrix &HLM)
VP_EXPLICIT vpTemplateTrackerMIForwardCompositional(vpTemplateTrackerWarp *_warp)
vpHessienApproximationType ApproxHessian
vpHessienType hessianComputation
double getCost(const vpImage< unsigned char > &I, const vpColVector &tp) VP_OVERRIDE
void computeProba(int &nbpoint)
void computeHessien(vpMatrix &H)
vpTemplateTrackerMI(const vpTemplateTrackerMI &)=delete
vpImage< double > dIx
vpImage< double > dIy
void computeEvalRMS(const vpColVector &p)
void computeOptimalBrentGain(const vpImage< unsigned char > &I, vpColVector &tp, double tMI, vpColVector &direction, double &alpha)
unsigned int iterationMax
void initPosEvalRMS(const vpColVector &p)
vpTemplateTrackerPoint * ptTemplate
vpTemplateTrackerWarp * Warp
vpImage< double > BI
unsigned int templateSize
Error that can be emitted by the vpTracker class and its derivatives.
@ notEnoughPointError
Not enough point to track.