Visual Servoing Platform  version 3.0.1
 All Classes Namespaces Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
vpPoseVirtualVisualServoing.cpp
1 /****************************************************************************
2  *
3  * This file is part of the ViSP software.
4  * Copyright (C) 2005 - 2017 by Inria. All rights reserved.
5  *
6  * This software is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * ("GPL") version 2 as published by the Free Software Foundation.
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 http://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  * Pose computation.
32  *
33  * Authors:
34  * Eric Marchand
35  *
36  *****************************************************************************/
37 
43 #include <visp3/vision/vpPose.h>
44 #include <visp3/core/vpPoint.h>
45 #include <visp3/core/vpExponentialMap.h>
46 #include <visp3/core/vpRobust.h>
47 
55 void
57 {
58  try
59  {
60 
61  double residu_1 = 1e8 ;
62  double r =1e8-1;
63 
64  // we stop the minimization when the error is bellow 1e-8
65 
66  int iter = 0 ;
67 
68  unsigned int nb = (unsigned int) listP.size() ;
69  vpMatrix L(2*nb,6) ;
70  vpColVector err(2*nb) ;
71  vpColVector sd(2*nb),s(2*nb) ;
72  vpColVector v ;
73 
74  vpPoint P;
75  std::list<vpPoint> lP ;
76 
77  // create sd
78  unsigned int k =0 ;
79  for (std::list<vpPoint>::const_iterator it = listP.begin(); it != listP.end(); ++it)
80  {
81  P = *it;
82  sd[2*k] = P.get_x() ;
83  sd[2*k+1] = P.get_y() ;
84  lP.push_back(P);
85  k ++;
86  }
87 
88  vpHomogeneousMatrix cMoPrev = cMo;
89  //while((int)((residu_1 - r)*1e12) !=0)
90  while(std::fabs((residu_1 - r)*1e12) > std::numeric_limits<double>::epsilon())
91  {
92  residu_1 = r ;
93 
94  // Compute the interaction matrix and the error
95  k =0 ;
96  for (std::list<vpPoint>::const_iterator it = lP.begin(); it != lP.end(); ++it)
97  {
98  P = *it;
99  // forward projection of the 3D model for a given pose
100  // change frame coordinates
101  // perspective projection
102  P.track(cMo) ;
103 
104  double x = s[2*k] = P.get_x(); /* point projected from cMo */
105  double y = s[2*k+1] = P.get_y();
106  double Z = P.get_Z() ;
107  L[2*k][0] = -1/Z ;
108  L[2*k][1] = 0 ;
109  L[2*k][2] = x/Z ;
110  L[2*k][3] = x*y ;
111  L[2*k][4] = -(1+x*x) ;
112  L[2*k][5] = y ;
113 
114  L[2*k+1][0] = 0 ;
115  L[2*k+1][1] = -1/Z ;
116  L[2*k+1][2] = y/Z ;
117  L[2*k+1][3] = 1+y*y ;
118  L[2*k+1][4] = -x*y ;
119  L[2*k+1][5] = -x ;
120 
121  k+=1 ;
122  }
123  err = s - sd ;
124 
125  // compute the residual
126  r = err.sumSquare() ;
127 
128  // compute the pseudo inverse of the interaction matrix
129  vpMatrix Lp ;
130  L.pseudoInverse(Lp,1e-16) ;
131 
132  // compute the VVS control law
133  v = -lambda*Lp*err ;
134 
135  //std::cout << "r=" << r <<std::endl ;
136  // update the pose
137 
138  cMoPrev = cMo;
139  cMo = vpExponentialMap::direct(v).inverse()*cMo ; ;
140  if (iter++>vvsIterMax) break ;
141  }
142 
143  if(computeCovariance)
144  covarianceMatrix = vpMatrix::computeCovarianceMatrixVVS(cMoPrev, err, L);
145  }
146 
147  catch(...)
148  {
149  vpERROR_TRACE(" ") ;
150  throw ;
151  }
152 }
153 
161 void
163 {
164  try{
165 
166  double residu_1 = 1e8 ;
167  double r =1e8-1;
168 
169  // we stop the minimization when the error is bellow 1e-8
170  vpMatrix W ;
171  vpRobust robust((unsigned int)(2*listP.size())) ;
172  robust.setThreshold(0.0000) ;
173  vpColVector w,res ;
174 
175  unsigned int nb = (unsigned int) listP.size() ;
176  vpMatrix L(2*nb,6) ;
177  vpColVector error(2*nb) ;
178  vpColVector sd(2*nb),s(2*nb) ;
179  vpColVector v ;
180 
181  listP.front() ;
182  vpPoint P;
183  std::list<vpPoint> lP ;
184 
185  // create sd
186  unsigned int k_ =0 ;
187  for (std::list<vpPoint>::const_iterator it = listP.begin(); it != listP.end(); ++it)
188  {
189  P = *it;
190  sd[2*k_] = P.get_x() ;
191  sd[2*k_+1] = P.get_y() ;
192  lP.push_back(P) ;
193  k_ ++;
194  }
195  int iter = 0 ;
196  res.resize(s.getRows()/2) ;
197  w.resize(s.getRows()/2) ;
198  W.resize(s.getRows(), s.getRows()) ;
199  w =1 ;
200 
201  //while((int)((residu_1 - r)*1e12) !=0)
202  while(std::fabs((residu_1 - r)*1e12) > std::numeric_limits<double>::epsilon())
203  {
204  residu_1 = r ;
205 
206  // Compute the interaction matrix and the error
207  k_ =0 ;
208  for (std::list<vpPoint>::const_iterator it = lP.begin(); it != lP.end(); ++it)
209  {
210  P = *it;
211  // forward projection of the 3D model for a given pose
212  // change frame coordinates
213  // perspective projection
214  P.track(cMo) ;
215 
216  double x = s[2*k_] = P.get_x(); // point projected from cMo
217  double y = s[2*k_+1] = P.get_y();
218  double Z = P.get_Z() ;
219  L[2*k_][0] = -1/Z ;
220  L[2*k_][1] = 0 ;
221  L[2*k_][2] = x/Z ;
222  L[2*k_][3] = x*y ;
223  L[2*k_][4] = -(1+x*x) ;
224  L[2*k_][5] = y ;
225 
226  L[2*k_+1][0] = 0 ;
227  L[2*k_+1][1] = -1/Z ;
228  L[2*k_+1][2] = y/Z ;
229  L[2*k_+1][3] = 1+y*y ;
230  L[2*k_+1][4] = -x*y ;
231  L[2*k_+1][5] = -x ;
232 
233  k_ ++;
234 
235  }
236  error = s - sd ;
237 
238  // compute the residual
239  r = error.sumSquare() ;
240 
241  for(unsigned int k=0 ; k <error.getRows()/2 ; k++)
242  {
243  res[k] = vpMath::sqr(error[2*k]) + vpMath::sqr(error[2*k+1]) ;
244  }
245  robust.setIteration(0);
246  robust.MEstimator(vpRobust::TUKEY, res, w);
247 
248  // compute the pseudo inverse of the interaction matrix
249  for (unsigned int k=0 ; k < error.getRows()/2 ; k++)
250  {
251  W[2*k][2*k] = w[k] ;
252  W[2*k+1][2*k+1] = w[k] ;
253  }
254  // compute the pseudo inverse of the interaction matrix
255  vpMatrix Lp ;
256  (W*L).pseudoInverse(Lp,1e-6) ;
257 
258  // compute the VVS control law
259  v = -lambda*Lp*W*error ;
260 
261  cMo = vpExponentialMap::direct(v).inverse()*cMo ; ;
262  if (iter++>vvsIterMax) break ;
263  }
264 
265  if(computeCovariance)
266  covarianceMatrix = vpMatrix::computeCovarianceMatrix(L,v,-lambda*error, W*W); // Remark: W*W = W*W.t() since the matrix is diagonale, but using W*W is more efficient.
267  }
268  catch(...)
269  {
270  vpERROR_TRACE(" ") ;
271  throw ;
272  }
273 
274 }
275 
276 
Implementation of a matrix and operations on matrices.
Definition: vpMatrix.h:97
static vpMatrix computeCovarianceMatrixVVS(const vpHomogeneousMatrix &cMo, const vpColVector &deltaS, const vpMatrix &Ls, const vpMatrix &W)
void MEstimator(const vpRobustEstimatorType method, const vpColVector &residues, vpColVector &weights)
Compute the weights according a residue vector and a PsiFunction.
Definition: vpRobust.cpp:182
void poseVirtualVSrobust(vpHomogeneousMatrix &cMo)
Compute the pose using virtual visual servoing approach and a robust control law. ...
void resize(const unsigned int nrows, const unsigned int ncols, const bool flagNullify=true)
Definition: vpArray2D.h:167
Implementation of an homogeneous matrix and operations on such kind of matrices.
#define vpERROR_TRACE
Definition: vpDebug.h:391
void track(const vpHomogeneousMatrix &cMo)
double get_y() const
Get the point y coordinate in the image plane.
Definition: vpPoint.cpp:458
std::list< vpPoint > listP
Array of point (use here class vpPoint)
Definition: vpPose.h:101
static vpMatrix computeCovarianceMatrix(const vpMatrix &A, const vpColVector &x, const vpColVector &b)
void poseVirtualVS(vpHomogeneousMatrix &cMo)
Compute the pose using virtual visual servoing approach.
Class that defines what is a point.
Definition: vpPoint.h:59
double lambda
parameters use for the virtual visual servoing approach
Definition: vpPose.h:106
static double sqr(double x)
Definition: vpMath.h:110
double get_x() const
Get the point x coordinate in the image plane.
Definition: vpPoint.cpp:456
unsigned int getRows() const
Return the number of rows of the 2D array.
Definition: vpArray2D.h:152
double get_Z() const
Get the point Z coordinate in the camera frame.
Definition: vpPoint.cpp:442
double sumSquare() const
Implementation of column vector and the associated operations.
Definition: vpColVector.h:72
vpHomogeneousMatrix inverse() const
static vpHomogeneousMatrix direct(const vpColVector &v)
Contains an M-Estimator and various influence function.
Definition: vpRobust.h:60
vpMatrix pseudoInverse(double svThreshold=1e-6) const
Compute the pseudo inverse of the matrix using the SVD.
Definition: vpMatrix.cpp:1741
void setThreshold(const double noise_threshold)
Definition: vpRobust.h:129
void setIteration(const unsigned int iter)
Set iteration.
Definition: vpRobust.h:123
void resize(const unsigned int i, const bool flagNullify=true)
Definition: vpColVector.h:225