ViSP  2.8.0
vpCalibration.cpp
1 /****************************************************************************
2  *
3  * $Id: vpCalibration.cpp 4317 2013-07-17 09:40:17Z fspindle $
4  *
5  * This file is part of the ViSP software.
6  * Copyright (C) 2005 - 2013 by INRIA. All rights reserved.
7  *
8  * This software is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * ("GPL") version 2 as published by the Free Software Foundation.
11  * See the file LICENSE.txt at the root directory of this source
12  * distribution for additional information about the GNU GPL.
13  *
14  * For using ViSP with software that can not be combined with the GNU
15  * GPL, please contact INRIA about acquiring a ViSP Professional
16  * Edition License.
17  *
18  * See http://www.irisa.fr/lagadic/visp/visp.html for more information.
19  *
20  * This software was developed at:
21  * INRIA Rennes - Bretagne Atlantique
22  * Campus Universitaire de Beaulieu
23  * 35042 Rennes Cedex
24  * France
25  * http://www.irisa.fr/lagadic
26  *
27  * If you have questions regarding the use of this file, please contact
28  * INRIA at visp@inria.fr
29  *
30  * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
31  * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
32  *
33  *
34  * Description:
35  * Camera calibration.
36  *
37  * Authors:
38  * Eric Marchand
39  * Francois Chaumette
40  * Anthony Saunier
41  *
42  *****************************************************************************/
43 
44 
50 #include <visp/vpCalibration.h>
51 #include <visp/vpDebug.h>
52 #include <visp/vpPose.h>
53 #include <visp/vpPixelMeterConversion.h>
54 
55 double vpCalibration::threshold = 1e-10f;
56 unsigned int vpCalibration::nbIterMax = 4000;
57 double vpCalibration::gain = 0.25;
62 {
63  npt = 0 ;
64 
65  LoX.clear() ;
66  LoY.clear() ;
67  LoZ.clear() ;
68  Lip.clear() ;
69 
70  return 0 ;
71 }
72 
74 {
75  init() ;
76 }
77 
78 
83 {
84  clearPoint() ;
85 }
86 
92 void vpCalibration::operator=(vpCalibration& twinCalibration )
93  {
94  npt = twinCalibration.npt ;
95  LoX = twinCalibration.LoX ;
96  LoY = twinCalibration.LoY ;
97  LoZ = twinCalibration.LoZ ;
98  Lip = twinCalibration.Lip ;
99 
100  residual = twinCalibration.residual;
101  cMo = twinCalibration.cMo;
102  residual_dist = twinCalibration.residual_dist;
103  cMo_dist = twinCalibration.cMo_dist ;
104 
105  cam = twinCalibration.cam ;
106  cam_dist = twinCalibration.cam_dist ;
107 
108  rMe = twinCalibration.rMe;
109 
110  eMc = twinCalibration.eMc;
111  eMc_dist = twinCalibration.eMc_dist;
112 }
113 
114 
119 {
120  LoX.clear() ;
121  LoY.clear() ;
122  LoZ.clear() ;
123  Lip.clear() ;
124  npt = 0 ;
125 
126  return 0 ;
127 }
128 
135 int vpCalibration::addPoint(double X, double Y, double Z, vpImagePoint &ip)
136 {
137  LoX.push_back(X);
138  LoY.push_back(Y);
139  LoZ.push_back(Z);
140 
141  Lip.push_back(ip);
142 
143  npt++ ;
144 
145  return 0 ;
146 }
147 
153 void
154  vpCalibration::computePose(const vpCameraParameters &cam, vpHomogeneousMatrix &cMo)
155 {
156  // The vpPose class mainly contents a list of vpPoint (that is (X,Y,Z, x, y) )
157  vpPose pose ;
158  // the list of point is cleared (if that's not done before)
159  pose.clearPoint() ;
160  // we set the 3D points coordinates (in meter !) in the object/world frame
161  std::list<double>::const_iterator it_LoX = LoX.begin();
162  std::list<double>::const_iterator it_LoY = LoY.begin();
163  std::list<double>::const_iterator it_LoZ = LoZ.begin();
164  std::list<vpImagePoint>::const_iterator it_Lip = Lip.begin();
165 
166  for (unsigned int i =0 ; i < npt ; i++)
167  {
168  vpPoint P;
169  P.setWorldCoordinates(*it_LoX, *it_LoY, *it_LoZ);
170  double x=0,y=0 ;
171  vpPixelMeterConversion::convertPoint(cam, *it_Lip, x,y) ;
172  P.set_x(x) ;
173  P.set_y(y) ;
174 
175  pose.addPoint(P);
176  ++it_LoX;
177  ++it_LoY;
178  ++it_LoZ;
179  ++it_Lip;
180  }
181  vpHomogeneousMatrix cMo_dementhon; // computed pose with dementhon
182  vpHomogeneousMatrix cMo_lagrange; // computed pose with dementhon
183 
184  // compute the initial pose using Lagrange method followed by a non linear
185  // minimisation method
186  // Pose by Lagrange it provides an initialization of the pose
187  pose.computePose(vpPose::LAGRANGE, cMo_lagrange) ;
188  double residual_lagrange = pose.computeResidual(cMo_lagrange);
189 
190  // compute the initial pose using Dementhon method followed by a non linear
191  // minimisation method
192  // Pose by Dementhon it provides an initialization of the pose
193  pose.computePose(vpPose::DEMENTHON, cMo_dementhon) ;
194  double residual_dementhon = pose.computeResidual(cMo_dementhon);
195 
196  //we keep the better initialization
197  if (residual_lagrange < residual_dementhon)
198  cMo = cMo_lagrange;
199  else
200  cMo = cMo_dementhon;
201 
202  // the pose is now refined using the virtual visual servoing approach
203  // Warning: cMo needs to be initialized otherwise it may diverge
204  pose.computePose(vpPose::VIRTUAL_VS, cMo) ;
205 
206 }
207 
215 double
217  vpCameraParameters& cam)
218 {
219  double residual = 0 ;
220 
221  std::list<double>::const_iterator it_LoX = LoX.begin();
222  std::list<double>::const_iterator it_LoY = LoY.begin();
223  std::list<double>::const_iterator it_LoZ = LoZ.begin();
224  std::list<vpImagePoint>::const_iterator it_Lip = Lip.begin();
225 
226  double u0 = cam.get_u0() ;
227  double v0 = cam.get_v0() ;
228  double px = cam.get_px() ;
229  double py = cam.get_py() ;
230  vpImagePoint ip;
231 
232  for (unsigned int i =0 ; i < npt ; i++)
233  {
234 
235  double oX = *it_LoX;
236  double oY = *it_LoY;
237  double oZ = *it_LoZ;
238 
239  double cX = oX*cMo[0][0]+oY*cMo[0][1]+oZ*cMo[0][2] + cMo[0][3];
240  double cY = oX*cMo[1][0]+oY*cMo[1][1]+oZ*cMo[1][2] + cMo[1][3];
241  double cZ = oX*cMo[2][0]+oY*cMo[2][1]+oZ*cMo[2][2] + cMo[2][3];
242 
243  double x = cX/cZ ;
244  double y = cY/cZ ;
245 
246  ip = *it_Lip;
247  double u = ip.get_u() ;
248  double v = ip.get_v() ;
249 
250  double xp = u0 + x*px;
251  double yp = v0 + y*py;
252 
253  residual += (vpMath::sqr(xp-u) + vpMath::sqr(yp-v)) ;
254 
255  ++it_LoX;
256  ++it_LoY;
257  ++it_LoZ;
258  ++it_Lip;
259  }
260  this->residual = residual ;
261  return sqrt(residual/npt) ;
262 }
270 double
272  vpCameraParameters& cam)
273 {
274  double residual = 0 ;
275 
276  std::list<double>::const_iterator it_LoX = LoX.begin();
277  std::list<double>::const_iterator it_LoY = LoY.begin();
278  std::list<double>::const_iterator it_LoZ = LoZ.begin();
279  std::list<vpImagePoint>::const_iterator it_Lip = Lip.begin();
280 
281  double u0 = cam.get_u0() ;
282  double v0 = cam.get_v0() ;
283  double px = cam.get_px() ;
284  double py = cam.get_py() ;
285  double kud = cam.get_kud() ;
286  double kdu = cam.get_kdu() ;
287 
288  double inv_px = 1/px;
289  double inv_py = 1/px;
290  vpImagePoint ip;
291 
292  for (unsigned int i =0 ; i < npt ; i++)
293  {
294 
295  double oX = *it_LoX;
296  double oY = *it_LoY;
297  double oZ = *it_LoZ;
298 
299  double cX = oX*cMo[0][0]+oY*cMo[0][1]+oZ*cMo[0][2] + cMo[0][3];
300  double cY = oX*cMo[1][0]+oY*cMo[1][1]+oZ*cMo[1][2] + cMo[1][3];
301  double cZ = oX*cMo[2][0]+oY*cMo[2][1]+oZ*cMo[2][2] + cMo[2][3];
302 
303  double x = cX/cZ ;
304  double y = cY/cZ ;
305 
306  ip = *it_Lip;
307  double u = ip.get_u() ;
308  double v = ip.get_v() ;
309 
310  double r2ud = 1+kud*(vpMath::sqr(x)+vpMath::sqr(y)) ;
311 
312  double xp = u0 + x*px*r2ud;
313  double yp = v0 + y*py*r2ud;
314 
315  residual += (vpMath::sqr(xp-u) + vpMath::sqr(yp-v)) ;
316 
317  double r2du = (vpMath::sqr((u-u0)*inv_px)+vpMath::sqr((v-v0)*inv_py)) ;
318 
319  xp = u0 + x*px - kdu*(u-u0)*r2du;
320  yp = v0 + y*py - kdu*(v-v0)*r2du;
321 
322  residual += (vpMath::sqr(xp-u) + vpMath::sqr(yp-v)) ;
323  ++it_LoX;
324  ++it_LoY;
325  ++it_LoZ;
326  ++it_Lip;
327  }
328  residual /=2;
329 
330  this->residual_dist = residual;
331  return sqrt(residual/npt) ;
332 }
333 
340 void
341  vpCalibration::computeStdDeviation(double &deviation,double &deviation_dist)
342 {
343  deviation = computeStdDeviation(cMo,cam);
344  deviation_dist = computeStdDeviation_dist(cMo_dist,cam_dist);
345 }
346 
347 
360  vpHomogeneousMatrix &cMo,
361  vpCameraParameters &cam,
362  bool verbose)
363 {
364  try{
365  computePose(cam,cMo);
366  switch (method)
367  {
368  case CALIB_LAGRANGE :
370  {
371  calibLagrange(cam, cMo);
372  }
373  break;
374  case CALIB_VIRTUAL_VS:
377  default:
378  break;
379  }
380 
381  switch (method)
382  {
383  case CALIB_VIRTUAL_VS:
387  {
388  if (verbose){std::cout << "start calibration without distortion"<< std::endl;}
389  calibVVS(cam, cMo, verbose);
390  }
391  break ;
392  case CALIB_LAGRANGE:
393  default:
394  break;
395  }
396  this->cMo = cMo;
397  this->cMo_dist = cMo;
398 
399  //Print camera parameters
400  if(verbose){
401  // std::cout << "Camera parameters without distortion :" << std::endl;
402  cam.printParameters();
403  }
404 
405  this->cam = cam;
406 
407  switch (method)
408  {
411  {
412  if (verbose){std::cout << "start calibration with distortion"<< std::endl;}
413  calibVVSWithDistortion(cam, cMo, verbose);
414  }
415  break ;
416  case CALIB_LAGRANGE:
417  case CALIB_VIRTUAL_VS:
419  default:
420  break;
421  }
422  //Print camera parameters
423  if(verbose){
424  // std::cout << "Camera parameters without distortion :" << std::endl;
425  this->cam.printParameters();
426  // std::cout << "Camera parameters with distortion :" << std::endl;
427  cam.printParameters();
428  }
429 
430  this->cam_dist = cam ;
431 
432  this->cMo_dist = cMo;
433  return 0 ;
434  }
435  catch(...){
436  throw;
437  }
438 }
439 
453  std::vector<vpCalibration> &table_cal,
454  vpCameraParameters& cam,
455  double &globalReprojectionError,
456  bool verbose)
457 {
458  try{
459  unsigned int nbPose = (unsigned int) table_cal.size();
460  for(unsigned int i=0;i<nbPose;i++){
461  if(table_cal[i].get_npt()>3)
462  table_cal[i].computePose(cam,table_cal[i].cMo);
463  }
464  switch (method) {
465  case CALIB_LAGRANGE :
466  if(nbPose > 1){
467  std::cout << "this calibration method is not available in" << std::endl
468  << "vpCalibration::computeCalibrationMulti()" << std::endl;
469  return -1 ;
470  }
471  else {
472  table_cal[0].calibLagrange(cam,table_cal[0].cMo);
473  table_cal[0].cam = cam ;
474  table_cal[0].cam_dist = cam ;
475  table_cal[0].cMo_dist = table_cal[0].cMo ;
476  }
477  break;
480  if(nbPose > 1){
481  std::cout << "this calibration method is not available in" << std::endl
482  << "vpCalibration::computeCalibrationMulti()" << std::endl
483  << "with several images." << std::endl;
484  return -1 ;
485  }
486  else {
487  table_cal[0].calibLagrange(cam,table_cal[0].cMo);
488  table_cal[0].cam = cam ;
489  table_cal[0].cam_dist = cam ;
490  table_cal[0].cMo_dist = table_cal[0].cMo ;
491  }
492  case CALIB_VIRTUAL_VS:
494  {
495  calibVVSMulti(table_cal, cam, globalReprojectionError, verbose);
496  }
497  break ;
498  }
499  //Print camera parameters
500  if(verbose){
501  // std::cout << "Camera parameters without distortion :" << std::endl;
502  cam.printParameters();
503  }
504 
505  switch (method)
506  {
507  case CALIB_LAGRANGE :
509  case CALIB_VIRTUAL_VS:
510  verbose = false ;
511  break;
514  {
515  if(verbose)
516  std::cout << "Compute camera parameters with distortion"<<std::endl;
517 
518  calibVVSWithDistortionMulti(table_cal, cam, globalReprojectionError, verbose);
519  }
520  break ;
521  }
522  //Print camera parameters
523  if(verbose){
524  // std::cout << "Camera parameters without distortion :" << std::endl;
525  table_cal[0].cam.printParameters();
526  // std::cout << "Camera parameters with distortion:" << std::endl;
527  cam.printParameters();
528  std::cout<<std::endl;
529  }
530  return 0 ;
531  }
532  catch(...){ throw; }
533 }
534 
550 int vpCalibration::computeCalibrationTsai(std::vector<vpCalibration> &table_cal,
551  vpHomogeneousMatrix& eMc,
552  vpHomogeneousMatrix& eMc_dist)
553 {
554  try{
555  unsigned int nbPose = (unsigned int)table_cal.size();
556  if (nbPose > 2){
557  std::vector<vpHomogeneousMatrix> table_cMo(nbPose);
558  std::vector<vpHomogeneousMatrix> table_cMo_dist(nbPose);
559  std::vector<vpHomogeneousMatrix> table_rMe(nbPose);
560 
561  for(unsigned int i=0;i<nbPose;i++){
562  table_cMo[i] = table_cal[i].cMo;
563  table_cMo_dist[i] = table_cal[i].cMo_dist;
564  table_rMe[i] = table_cal[i].rMe;
565  }
566  calibrationTsai(table_cMo, table_rMe, eMc);
567  calibrationTsai(table_cMo_dist, table_rMe, eMc_dist);
568 
569  return 0;
570  }
571  else{
572  vpERROR_TRACE("Three images are needed to compute Tsai calibration !\n");
573  return -1;
574  }
575  }
576  catch(...){
577  throw;
578  }
579 }
580 
581 
589 int vpCalibration::writeData(const char *filename)
590 {
591  std::ofstream f(filename) ;
592  vpImagePoint ip;
593 
594  std::list<double>::const_iterator it_LoX = LoX.begin();
595  std::list<double>::const_iterator it_LoY = LoY.begin();
596  std::list<double>::const_iterator it_LoZ = LoZ.begin();
597  std::list<vpImagePoint>::const_iterator it_Lip = Lip.begin();
598 
599  f.precision(10);
600  f.setf(std::ios::fixed,std::ios::floatfield);
601  f << LoX.size() << std::endl ;
602 
603  for (unsigned int i =0 ; i < LoX.size() ; i++)
604  {
605 
606  double oX = *it_LoX;
607  double oY = *it_LoY;
608  double oZ = *it_LoZ;
609 
610  ip = *it_Lip;
611  double u = ip.get_u() ;
612  double v = ip.get_v() ;
613 
614  f << oX <<" " << oY << " " << oZ << " " << u << " " << v <<std::endl ;
615 
616  ++it_LoX;
617  ++it_LoY;
618  ++it_LoZ;
619  ++it_Lip;
620 
621  }
622 
623  f.close() ;
624  return 0 ;
625 }
626 
633 int vpCalibration::readData(const char* filename)
634 {
635  vpImagePoint ip;
636  std::ifstream f;
637  f.open(filename);
638  if (f != NULL){
639  int n ;
640  f >> n ;
641  std::cout << "There are "<< n <<" point on the calibration grid " << std::endl ;
642 
643  clearPoint() ;
644  for (int i=0 ; i < n ; i++)
645  {
646  double x, y, z, u, v ;
647  f >> x >> y >> z >> u >> v ;
648  std::cout << x <<" "<<y <<" "<<z<<" "<<u<<" "<<v <<std::endl ;
649  ip.set_u( u );
650  ip.set_v( v );
651  addPoint(x, y, z, ip) ;
652  }
653 
654  f.close() ;
655  return 0 ;
656  }
657  else{
658  return -1;
659  }
660 }
677 int vpCalibration::readGrid(const char* filename, unsigned int &n,
678  std::list<double> &oX, std::list<double> &oY, std::list<double> &oZ, bool verbose)
679 {
680  try{
681  std::ifstream f;
682  f.open(filename);
683  if (f != NULL){
684 
685  f >> n ;
686  if(verbose)
687  std::cout << "There are "<< n <<" points on the calibration grid " << std::endl ;
688  int no_pt;
689  double x,y,z;
690 
691  // clear the list
692  oX.clear();
693  oY.clear();
694  oZ.clear();
695 
696  for (unsigned int i=0 ; i < n ; i++)
697  {
698  f >> no_pt >> x >> y >> z ;
699  if(verbose){
700  std::cout << no_pt <<std::endl ;
701  std::cout << x <<" "<< y <<" "<< z <<std::endl ;
702  }
703  oX.push_back(x) ;
704  oY.push_back(y) ;
705  oZ.push_back(z) ;
706  }
707 
708  f.close() ;
709  }
710  else{
711  return -1;
712  }
713  }
714  catch(...){return -1;}
715  return 0 ;
716 }
717 
726  unsigned int thickness)
727 {
728 
729  for (std::list<vpImagePoint>::const_iterator it = Lip.begin(); it != Lip.end(); ++ it) {
730  vpDisplay::displayCross(I, *it, 12, color, thickness) ;
731  }
732  return 0 ;
733 }
734 
743  unsigned int thickness)
744 {
745  double u0_dist = cam_dist.get_u0() ;
746  double v0_dist = cam_dist.get_v0() ;
747  double px_dist = cam_dist.get_px() ;
748  double py_dist = cam_dist.get_py() ;
749  double kud_dist = cam_dist.get_kud() ;
750  // double kdu_dist = cam_dist.get_kdu() ;
751 
752  // double u0 = cam.get_u0() ;
753  // double v0 = cam.get_v0() ;
754  // double px = cam.get_px() ;
755  // double py = cam.get_py() ;
756 
757  std::list<double>::const_iterator it_LoX = LoX.begin();
758  std::list<double>::const_iterator it_LoY = LoY.begin();
759  std::list<double>::const_iterator it_LoZ = LoZ.begin();
760 
761  for (unsigned int i =0 ; i < npt ; i++)
762  {
763 
764  double oX = *it_LoX;
765  double oY = *it_LoY;
766  double oZ = *it_LoZ;
767 
768  double cX = oX*cMo[0][0]+oY*cMo[0][1]+oZ*cMo[0][2] + cMo[0][3];
769  double cY = oX*cMo[1][0]+oY*cMo[1][1]+oZ*cMo[1][2] + cMo[1][3];
770  double cZ = oX*cMo[2][0]+oY*cMo[2][1]+oZ*cMo[2][2] + cMo[2][3];
771 
772  double x = cX/cZ ;
773  double y = cY/cZ ;
774 
775  // double xp = u0 + x*px ;
776  // double yp = v0 + y*py ;
777 
778  // vpDisplay::displayCross(I,(int)vpMath::round(yp), (int)vpMath::round(xp),
779  // 5,col) ;
780 
781  cX = oX*cMo_dist[0][0]+oY*cMo_dist[0][1]+oZ*cMo_dist[0][2]+cMo_dist[0][3];
782  cY = oX*cMo_dist[1][0]+oY*cMo_dist[1][1]+oZ*cMo_dist[1][2]+cMo_dist[1][3];
783  cZ = oX*cMo_dist[2][0]+oY*cMo_dist[2][1]+oZ*cMo_dist[2][2]+cMo_dist[2][3];
784 
785  x = cX/cZ ;
786  y = cY/cZ ;
787 
788  double r2 = 1+kud_dist*(vpMath::sqr(x)+vpMath::sqr(y)) ;
789 
790  vpImagePoint ip;
791  ip.set_u( u0_dist + x*px_dist*r2 );
792  ip.set_v( v0_dist + y*py_dist*r2 );
793 
794  vpDisplay::displayCross(I, ip, 6, color, thickness) ;
796 
797  // std::cout << oX << " " << oY << " " <<oZ << std::endl ;
798  // I.getClick() ;
799  ++it_LoX;
800  ++it_LoY;
801  ++it_LoZ;
802  }
803  return 0;
804 }
805 
806 #ifdef VISP_BUILD_DEPRECATED_FUNCTIONS
807 
824  unsigned int nbPose,
825  vpCalibration table_cal[],
826  vpCameraParameters& cam,
827  bool verbose)
828 {
829  try{
830  for(unsigned int i=0;i<nbPose;i++){
831  if(table_cal[i].get_npt()>3)
832  table_cal[i].computePose(cam,table_cal[i].cMo);
833  }
834  switch (method) {
835  case CALIB_LAGRANGE :
836  if(nbPose > 1){
837  std::cout << "this calibration method is not available in" << std::endl
838  << "vpCalibration::computeCalibrationMulti()" << std::endl;
839  return -1 ;
840  }
841  else {
842  table_cal[0].calibLagrange(cam,table_cal[0].cMo);
843  table_cal[0].cam = cam ;
844  table_cal[0].cam_dist = cam ;
845  table_cal[0].cMo_dist = table_cal[0].cMo ;
846  }
847  break;
850  if(nbPose > 1){
851  std::cout << "this calibration method is not available in" << std::endl
852  << "vpCalibration::computeCalibrationMulti()" << std::endl
853  << "with several images." << std::endl;
854  return -1 ;
855  }
856  else {
857  table_cal[0].calibLagrange(cam,table_cal[0].cMo);
858  table_cal[0].cam = cam ;
859  table_cal[0].cam_dist = cam ;
860  table_cal[0].cMo_dist = table_cal[0].cMo ;
861  }
862  case CALIB_VIRTUAL_VS:
864  {
865  calibVVSMulti(nbPose, table_cal, cam, verbose);
866  }
867  break ;
868  }
869  //Print camera parameters
870  if(verbose){
871  // std::cout << "Camera parameters without distortion :" << std::endl;
872  cam.printParameters();
873  }
874 
875  switch (method)
876  {
877  case CALIB_LAGRANGE :
879  case CALIB_VIRTUAL_VS:
880  verbose = false ;
881  break;
884  {
885  if(verbose)
886  std::cout << "Compute camera parameters with distortion"<<std::endl;
887 
888  calibVVSWithDistortionMulti(nbPose, table_cal, cam, verbose);
889  }
890  break ;
891  }
892  //Print camera parameters
893  if(verbose){
894  // std::cout << "Camera parameters without distortion :" << std::endl;
895  table_cal[0].cam.printParameters();
896  // std::cout << "Camera parameters with distortion:" << std::endl;
897  cam.printParameters();
898  std::cout<<std::endl;
899  }
900  return 0 ;
901  }
902  catch(...){ throw; }
903 }
904 
925  vpCalibration table_cal[],
926  vpHomogeneousMatrix& eMc,
927  vpHomogeneousMatrix& eMc_dist)
928 {
929  try{
930  if (nbPose > 2){
931  vpHomogeneousMatrix* table_cMo = new vpHomogeneousMatrix[nbPose];
932  vpHomogeneousMatrix* table_cMo_dist = new vpHomogeneousMatrix[nbPose];
933  vpHomogeneousMatrix* table_rMe = new vpHomogeneousMatrix[nbPose];
934 
935  for(unsigned int i=0;i<nbPose;i++){
936  table_cMo[i] = table_cal[i].cMo;
937  table_cMo_dist[i] = table_cal[i].cMo_dist;
938  table_rMe[i] = table_cal[i].rMe;
939  }
940  calibrationTsai(nbPose,table_cMo,table_rMe,eMc);
941  calibrationTsai(nbPose,table_cMo_dist,table_rMe,eMc_dist);
942 
943  delete [] table_cMo;
944  delete [] table_cMo_dist;
945  delete [] table_rMe;
946 
947  return 0;
948  }
949  else{
950  vpERROR_TRACE("Three images are needed to compute Tsai calibration !\n");
951  return -1;
952  }
953  }
954  catch(...){
955  throw;
956  }
957 }
958 
978 int vpCalibration::readGrid(const char* filename,unsigned int &n,
979  vpList<double> &oX,vpList<double> &oY,vpList<double> &oZ, bool verbose)
980 {
981  try{
982  std::ifstream f;
983  f.open(filename);
984  if (f != NULL){
985 
986  f >> n ;
987  if(verbose)
988  std::cout << "There are "<< n <<" points on the calibration grid " << std::endl ;
989  int no_pt;
990  double x,y,z;
991 
992  oX.front();
993  oY.front();
994  oZ.front();
995  for (unsigned int i=0 ; i < n ; i++)
996  {
997  f >> no_pt >> x >> y >> z ;
998  if(verbose){
999  std::cout << no_pt <<std::endl ;
1000  std::cout << x <<" "<< y <<" "<< z <<std::endl ;
1001  }
1002  oX.addRight(x) ;
1003  oY.addRight(y) ;
1004  oZ.addRight(z) ;
1005  }
1006 
1007  f.close() ;
1008  }
1009  else{
1010  return -1;
1011  }
1012  }
1013  catch(...){return -1;}
1014  return 0 ;
1015 }
1016 
1017 #endif // VISP_BUILD_DEPRECATED_FUNCTIONS
double get_v() const
Definition: vpImagePoint.h:250
double get_u0() const
vpCalibration()
Constructor.
int displayGrid(vpImage< unsigned char > &I, vpColor color=vpColor::yellow, unsigned int thickness=1)
The class provides a data structure for the homogeneous matrices as well as a set of operations on th...
#define vpERROR_TRACE
Definition: vpDebug.h:379
Provide simple list management.
Definition: vpList.h:112
int readData(const char *filename)
Class to define colors available for display functionnalities.
Definition: vpColor.h:125
double get_u() const
Definition: vpImagePoint.h:239
int addPoint(double X, double Y, double Z, vpImagePoint &ip)
void set_x(const double x)
Set the point x coordinate in the image plane.
Definition: vpPoint.h:194
static void convertPoint(const vpCameraParameters &cam, const double &u, const double &v, double &x, double &y)
Point coordinates conversion from pixel coordinates to normalized coordinates in meter...
double get_py() const
Tools for perspective camera calibration.
Definition: vpCalibration.h:78
virtual ~vpCalibration()
Destructor.
int computeCalibration(vpCalibrationMethodType method, vpHomogeneousMatrix &cMo, vpCameraParameters &cam, bool verbose=false)
double computeStdDeviation_dist(vpHomogeneousMatrix &cMo, vpCameraParameters &cam)
vpHomogeneousMatrix cMo
(as a 3x4 matrix [R T])
Definition: vpCalibration.h:92
Class that defines what is a point.
Definition: vpPoint.h:65
void operator=(vpCalibration &twinCalibration)
= operator
int displayData(vpImage< unsigned char > &I, vpColor color=vpColor::red, unsigned int thickness=1)
int clearPoint()
Suppress all the point in the array of point.
double get_v0() const
void set_u(const double u)
Definition: vpImagePoint.h:203
static double sqr(double x)
Definition: vpMath.h:106
void front(void)
Position the current element on the first element of the list.
Definition: vpList.h:386
vpHomogeneousMatrix cMo_dist
Definition: vpCalibration.h:94
virtual void displayCross(const vpImagePoint &ip, unsigned int size, const vpColor &color, unsigned int thickness=1)=0
void set_v(const double v)
Definition: vpImagePoint.h:214
Class used for pose computation from N points (pose from point only).
Definition: vpPose.h:78
Generic class defining intrinsic camera parameters.
void addRight(const type &el)
add a new element in the list, at the right of the current one
Definition: vpList.h:480
vpHomogeneousMatrix eMc_dist
void set_y(const double y)
Set the point y coordinate in the image plane.
Definition: vpPoint.h:196
unsigned int get_npt() const
get the number of points
double get_px() const
vpHomogeneousMatrix rMe
reference coordinates (manipulator base coordinates)
static void calibrationTsai(std::vector< vpHomogeneousMatrix > &cMo, std::vector< vpHomogeneousMatrix > &rMe, vpHomogeneousMatrix &eMc)
calibration method of effector-camera from R. Tsai and R. Lorenz .
double get_kud() const
vpCameraParameters cam_dist
projection model with distortion
Definition: vpCalibration.h:99
double get_kdu() const
int writeData(const char *filename)
vpHomogeneousMatrix eMc
position of the camera in relation to the effector
void computePose(vpPoseMethodType methode, vpHomogeneousMatrix &cMo)
compute the pose for a given method
Definition: vpPose.cpp:382
Class that defines a 2D point in an image. This class is useful for image processing and stores only ...
Definition: vpImagePoint.h:92
static int computeCalibrationTsai(std::vector< vpCalibration > &table_cal, vpHomogeneousMatrix &eMc, vpHomogeneousMatrix &eMc_dist)
Compute the multi-image calibration of effector-camera from R. Tsai and R. Lenz . ...
void computeStdDeviation(double &deviation, double &deviation_dist)
vpCameraParameters cam
projection model without distortion
Definition: vpCalibration.h:97
static int computeCalibrationMulti(vpCalibrationMethodType method, std::vector< vpCalibration > &table_cal, vpCameraParameters &cam, double &globalReprojectionError, bool verbose=false)
void addPoint(const vpPoint &P)
Add a new point in this array.
Definition: vpPose.cpp:150
double computeResidual(const vpHomogeneousMatrix &cMo) const
Compute and return the residual expressed in meter for the pose matrix 'cMo'.
Definition: vpPose.cpp:339
static int readGrid(const char *filename, unsigned int &n, std::list< double > &oX, std::list< double > &oY, std::list< double > &oZ, bool verbose=false)
void setWorldCoordinates(const double ox, const double oy, const double oz)
Set the point world coordinates. We mean here the coordinates of the point in the object frame...
Definition: vpPoint.cpp:74
void clearPoint()
suppress all the point in the array of point
Definition: vpPose.cpp:128