Skip to content

Commit 6486b17

Browse files
authored
Relpose estimation bug fix (colmap#171)
* fix the bug that relative pose estimation fails when camera model is not supported by poselib * allow the focal length to be different for unrecognized camera type
1 parent b464ef5 commit 6486b17

File tree

1 file changed

+43
-9
lines changed

1 file changed

+43
-9
lines changed

glomap/estimators/relpose_estimation.cc

Lines changed: 43 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -44,26 +44,60 @@ void EstimateRelativePoses(ViewGraph& view_graph,
4444
const Image& image2 = images[image_pair.image_id2];
4545
const Eigen::MatrixXi& matches = image_pair.matches;
4646

47+
const Camera& camera1 = cameras[image1.camera_id];
48+
const Camera& camera2 = cameras[image2.camera_id];
49+
poselib::Camera camera_poselib1 = ColmapCameraToPoseLibCamera(camera1);
50+
poselib::Camera camera_poselib2 = ColmapCameraToPoseLibCamera(camera2);
51+
bool valid_camera_model =
52+
(camera_poselib1.model_id >= 0 && camera_poselib2.model_id >= 0);
53+
4754
// Collect the original 2D points
4855
points2D_1.clear();
4956
points2D_2.clear();
5057
for (size_t idx = 0; idx < matches.rows(); idx++) {
5158
points2D_1.push_back(image1.features[matches(idx, 0)]);
5259
points2D_2.push_back(image2.features[matches(idx, 1)]);
5360
}
61+
// If the camera model is not supported by poselib
62+
if (!valid_camera_model) {
63+
// Undistort points
64+
// Note that here, we still rescale by the focal length (to avoid
65+
// change the RANSAC threshold)
66+
Eigen::Matrix2d K1_new = Eigen::Matrix2d::Zero();
67+
Eigen::Matrix2d K2_new = Eigen::Matrix2d::Zero();
68+
K1_new(0, 0) = camera1.FocalLengthX();
69+
K1_new(1, 1) = camera1.FocalLengthY();
70+
K2_new(0, 0) = camera2.FocalLengthX();
71+
K2_new(1, 1) = camera2.FocalLengthY();
72+
for (size_t idx = 0; idx < matches.rows(); idx++) {
73+
points2D_1[idx] = K1_new * camera1.CamFromImg(points2D_1[idx]);
74+
points2D_2[idx] = K2_new * camera2.CamFromImg(points2D_2[idx]);
75+
}
5476

77+
// Reset the camera to be the pinhole camera with original focal
78+
// length and zero principal point
79+
camera_poselib1 = poselib::Camera(
80+
"PINHOLE",
81+
{camera1.FocalLengthX(), camera1.FocalLengthY(), 0., 0.},
82+
camera1.width,
83+
camera1.height);
84+
camera_poselib2 = poselib::Camera(
85+
"PINHOLE",
86+
{camera2.FocalLengthX(), camera2.FocalLengthY(), 0., 0.},
87+
camera2.width,
88+
camera2.height);
89+
}
5590
inliers.clear();
5691
poselib::CameraPose pose_rel_calc;
5792
try {
58-
poselib::estimate_relative_pose(
59-
points2D_1,
60-
points2D_2,
61-
ColmapCameraToPoseLibCamera(cameras[image1.camera_id]),
62-
ColmapCameraToPoseLibCamera(cameras[image2.camera_id]),
63-
options.ransac_options,
64-
options.bundle_options,
65-
&pose_rel_calc,
66-
&inliers);
93+
poselib::estimate_relative_pose(points2D_1,
94+
points2D_2,
95+
camera_poselib1,
96+
camera_poselib2,
97+
options.ransac_options,
98+
options.bundle_options,
99+
&pose_rel_calc,
100+
&inliers);
67101
} catch (const std::exception& e) {
68102
LOG(ERROR) << "Error in relative pose estimation: " << e.what();
69103
image_pair.is_valid = false;

0 commit comments

Comments
 (0)