15 #include <mrpt/config.h> 16 #include <mrpt/otherlibs/do_opencv_includes.h> 20 #include <Eigen/Dense> 23 #include <opencv2/core/eigen.hpp> 36 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
37 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
38 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
39 Eigen::Ref<Eigen::MatrixXd> pose_mat)
43 #if MRPT_HAS_OPENCV == 1 46 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
49 if (img_pts.rows() != obj_pts.rows() ||
50 img_pts.cols() != obj_pts.cols())
52 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
55 if (obj_pts.rows() < obj_pts.cols())
57 cam_in_eig = cam_intrinsic.transpose();
58 img_pts_eig = img_pts.transpose().block(0, 0,
n, 2);
59 obj_pts_eig = obj_pts.transpose();
63 cam_in_eig = cam_intrinsic;
64 img_pts_eig = img_pts.block(0, 0,
n, 2);
65 obj_pts_eig = obj_pts;
69 Eigen::Matrix3d R_eig;
70 Eigen::MatrixXd t_eig;
73 cv::Mat cam_in_cv(3, 3, CV_32F), img_pts_cv(2,
n, CV_32F),
74 obj_pts_cv(3,
n, CV_32F), R_cv(3, 3, CV_32F), t_cv(3, 1, CV_32F);
76 cv::eigen2cv(cam_in_eig, cam_in_cv);
77 cv::eigen2cv(img_pts_eig, img_pts_cv);
78 cv::eigen2cv(obj_pts_eig, obj_pts_cv);
83 cv::cv2eigen(R_cv, R_eig);
84 cv::cv2eigen(t_cv, t_eig);
86 Eigen::Quaterniond
q(R_eig);
88 pose_mat << t_eig,
q.vec();
101 std::cout <<
"Please install OpenCV for DLS-PnP" << std::endl;
104 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 105 "of obj_pts and img_pts" 110 <<
"Camera intrinsic matrix does not have 3x3 dimensions " 119 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
120 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
121 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
122 Eigen::Ref<Eigen::MatrixXd> pose_mat)
126 #if MRPT_HAS_OPENCV == 1 129 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
132 if (img_pts.rows() != obj_pts.rows() ||
133 img_pts.cols() != obj_pts.cols())
135 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
138 if (obj_pts.rows() < obj_pts.cols())
140 cam_in_eig = cam_intrinsic.transpose();
141 img_pts_eig = img_pts.transpose().block(0, 0,
n, 2);
142 obj_pts_eig = obj_pts.transpose();
146 cam_in_eig = cam_intrinsic;
147 img_pts_eig = img_pts.block(0, 0,
n, 2);
148 obj_pts_eig = obj_pts;
152 Eigen::Matrix3d R_eig;
153 Eigen::MatrixXd t_eig;
156 cv::Mat cam_in_cv(3, 3, CV_32F), img_pts_cv(2,
n, CV_32F),
157 obj_pts_cv(3,
n, CV_32F), R_cv, t_cv;
159 cv::eigen2cv(cam_in_eig, cam_in_cv);
160 cv::eigen2cv(img_pts_eig, img_pts_cv);
161 cv::eigen2cv(obj_pts_eig, obj_pts_cv);
166 cv::cv2eigen(R_cv, R_eig);
167 cv::cv2eigen(t_cv, t_eig);
169 Eigen::Quaterniond
q(R_eig);
171 pose_mat << t_eig,
q.vec();
184 std::cout <<
"Please install OpenCV for DLS-PnP" << std::endl;
187 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 188 "of obj_pts and img_pts" 193 <<
"Camera intrinsic matrix does not have 3x3 dimensions " 202 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
203 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
204 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
205 Eigen::Ref<Eigen::MatrixXd> pose_mat)
209 #if MRPT_HAS_OPENCV == 1 212 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
215 if (img_pts.rows() != obj_pts.rows() ||
216 img_pts.cols() != obj_pts.cols())
218 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
221 if (obj_pts.rows() < obj_pts.cols())
223 cam_in_eig = cam_intrinsic.transpose();
224 img_pts_eig = img_pts.transpose().block(0, 0,
n, 2);
225 obj_pts_eig = obj_pts.transpose();
229 cam_in_eig = cam_intrinsic;
230 img_pts_eig = img_pts.block(0, 0,
n, 2);
231 obj_pts_eig = obj_pts;
235 Eigen::Matrix3d R_eig;
236 Eigen::MatrixXd t_eig;
239 cv::Mat cam_in_cv(3, 3, CV_32F), img_pts_cv(2,
n, CV_32F),
240 obj_pts_cv(3,
n, CV_32F), R_cv, t_cv;
242 cv::eigen2cv(cam_in_eig, cam_in_cv);
243 cv::eigen2cv(img_pts_eig, img_pts_cv);
244 cv::eigen2cv(obj_pts_eig, obj_pts_cv);
249 cv::cv2eigen(R_cv, R_eig);
250 cv::cv2eigen(t_cv, t_eig);
252 Eigen::Quaterniond
q(R_eig);
254 pose_mat << t_eig,
q.vec();
266 std::cout <<
"Please install OpenCV for DLS-PnP" << std::endl;
269 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 270 "of obj_pts and img_pts" 275 <<
"Camera intrinsic matrix does not have 3x3 dimensions " 284 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
285 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
286 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
287 Eigen::Ref<Eigen::MatrixXd> pose_mat)
292 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
295 if (img_pts.rows() != obj_pts.rows() ||
296 img_pts.cols() != obj_pts.cols())
298 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
301 if (obj_pts.rows() < obj_pts.cols())
303 cam_in_eig = cam_intrinsic.transpose();
304 img_pts_eig = img_pts.transpose().block(0, 0,
n, 2);
305 obj_pts_eig = obj_pts.transpose();
309 cam_in_eig = cam_intrinsic;
310 img_pts_eig = img_pts.block(0, 0,
n, 2);
311 obj_pts_eig = obj_pts;
320 bool ret =
p.solve(
R,
t, obj_pts_eig, img_pts_eig);
322 Eigen::Quaterniond
q(
R);
324 pose_mat <<
t,
q.vec();
333 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 334 "of obj_pts and img_pts" 339 <<
"Camera intrinsic matrix does not have 3x3 dimensions " 348 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
349 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
350 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
351 Eigen::Ref<Eigen::MatrixXd> pose_mat)
356 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
359 if (img_pts.rows() != obj_pts.rows() ||
360 img_pts.cols() != obj_pts.cols())
362 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
365 if (obj_pts.rows() < obj_pts.cols())
367 cam_in_eig = cam_intrinsic.transpose();
368 img_pts_eig = img_pts.transpose();
369 obj_pts_eig = obj_pts.transpose();
373 cam_in_eig = cam_intrinsic;
374 img_pts_eig = img_pts;
375 obj_pts_eig = obj_pts;
384 bool ret =
r.compute_pose(
R,
t);
386 Eigen::Quaterniond
q(
R);
388 pose_mat <<
t,
q.vec();
397 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 398 "of obj_pts and img_pts" 403 <<
"Camera intrinsic matrix does not have 3x3 dimensions " 412 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
413 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
414 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
415 Eigen::Ref<Eigen::MatrixXd> pose_mat)
420 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
423 if (img_pts.rows() != obj_pts.rows() ||
424 img_pts.cols() != obj_pts.cols())
426 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
429 if (obj_pts.rows() < obj_pts.cols())
431 cam_in_eig = cam_intrinsic.transpose();
432 img_pts_eig = img_pts.transpose();
433 obj_pts_eig = obj_pts.transpose();
437 cam_in_eig = cam_intrinsic;
438 img_pts_eig = img_pts;
439 obj_pts_eig = obj_pts;
449 bool ret =
p.compute_pose(
R,
t,
n);
451 Eigen::Quaterniond
q(
R);
453 pose_mat <<
t,
q.vec();
462 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 463 "of obj_pts and img_pts" 468 <<
"Camera intrinsic matrix does not have 3x3 dimensions " 477 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
478 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
479 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
480 Eigen::Ref<Eigen::MatrixXd> pose_mat)
485 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
488 if (img_pts.rows() != obj_pts.rows() ||
489 img_pts.cols() != obj_pts.cols())
491 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
494 if (obj_pts.rows() < obj_pts.cols())
496 cam_in_eig = cam_intrinsic.transpose();
497 img_pts_eig = img_pts.transpose().block(0, 0,
n, 2);
498 obj_pts_eig = obj_pts.transpose();
502 cam_in_eig = cam_intrinsic;
503 img_pts_eig = img_pts.block(0, 0,
n, 2);
504 obj_pts_eig = obj_pts;
514 bool ret =
p.compute_pose(
R,
t);
516 Eigen::Quaterniond
q(
R);
518 pose_mat <<
t,
q.vec();
527 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 528 "of obj_pts and img_pts" 533 <<
"Camera intrinsic matrix does not have 3x3 dimensions " 542 const Eigen::Ref<Eigen::MatrixXd> obj_pts,
543 const Eigen::Ref<Eigen::MatrixXd> img_pts,
int n,
544 const Eigen::Ref<Eigen::MatrixXd> cam_intrinsic,
545 Eigen::Ref<Eigen::MatrixXd> pose_mat)
550 Eigen::MatrixXd cam_in_eig, img_pts_eig, obj_pts_eig;
553 if (img_pts.rows() != obj_pts.rows() ||
554 img_pts.cols() != obj_pts.cols())
556 else if (cam_intrinsic.rows() != 3 || cam_intrinsic.cols() != 3)
559 if (obj_pts.rows() < obj_pts.cols())
561 cam_in_eig = cam_intrinsic.transpose();
562 img_pts_eig = img_pts.transpose();
563 obj_pts_eig = obj_pts.transpose();
567 cam_in_eig = cam_intrinsic;
568 img_pts_eig = img_pts;
569 obj_pts_eig = obj_pts;
581 Eigen::Quaterniond
q(
R);
583 pose_mat <<
t,
q.vec();
592 std::cout <<
"2d/3d correspondences mismatch\n Check dimension " 593 "of obj_pts and img_pts" 598 <<
"Camera intrinsic matrix does not have 3x3 dimensions " Unified PnP - Eigen Wrapper for OpenCV function.
bool compute_pose(cv::Mat &R, cv::Mat &t)
OpenCV function for computing pose.
PnP Algorithms toolkit for MRPT.
void compute_pose(cv::Mat &R, cv::Mat &t)
OpenCV wrapper to compute pose.
GLdouble GLdouble GLdouble GLdouble q
bool upnp(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
Unified-PnP (UPnP) : Algorithm to compute pose from unknown camera intrinsic matrix ...
Robust - PnP class definition for computing pose.
Lu Hage Mjolsness - Iterative PnP Algorithm (Eigen Implementation.
bool ppnp(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
Procrustes-PnP(PPnP) Algorithm : Iterative SVD based algorithm
bool rpnp(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
Robust (R-PnP)- A closed form solution with intermediate P3P computations
bool epnp(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
Efficient-PnP (EPnP) - Algorithm takes 4 control points based on n points and uses the control point...
Efficient PnP - Eigen Wrapper for OpenCV calib3d implementation.
bool lhm(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
Lu-Hager-Mjolsness(LHM)-PnP algorithm : Iterative algorithm to reduce object space error ...
bool compute_pose(Eigen::Ref< Eigen::Matrix3d > R_, Eigen::Ref< Eigen::Vector3d > t_)
Function to compute pose using LHM PnP algorithm.
GLdouble GLdouble GLdouble r
bool p3p(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
P3P - A closed form solution for n=3, 2D-3D correspondences
Pose from Orthogonality and Scaling (POSIT) - Eigen Implementation.
Direct Least Squares (DLS) - Eigen wrapper for OpenCV Implementation.
bool dls(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
Direct Least Squares (DLS) - PnP : Algorithm formulates position as a function of rotation...
bool posit(const Eigen::Ref< Eigen::MatrixXd > obj_pts, const Eigen::Ref< Eigen::MatrixXd > img_pts, int n, const Eigen::Ref< Eigen::MatrixXd > cam_intrinsic, Eigen::Ref< Eigen::MatrixXd > pose_mat)
Pose from Orthogoanlity and Scaling :Iterative (POSIT) - A Geometric algorithm to compute scale and ...
P3P Pose estimation Algorithm - Eigen Implementation.
double compute_pose(cv::Mat &R, cv::Mat &t)
Function to compute pose.