Quantcast
Channel: OpenCV Q&A Forum - Latest question feed
Viewing all articles
Browse latest Browse all 19555

findEssentialMat for coplanar points

$
0
0
[this is a copy of a [question I just posted on StackOverflow](http://stackoverflow.com/questions/36844139/opencv-findessentialmat)] I came to a conclusion that OpenCV's findEssentialMat is not working properly for coplanar points. The documentation specifies that it uses Nister's 5 point algorithm, and the corresponding paper declares that the algorithm works fine for coplanar points. void main() { ofstream log; log.open("errorLog.txt"); srand((time(NULL) % RAND_MAX) * RAND_MAX); /******* camera properties *******/ Mat camMat = Mat::eye(3, 3, CV_64F); Mat distCoeffs = Mat::zeros(4, 1, CV_64F); /******* pose 1 *******/ Mat rVec1 = (Mat_(3, 1) << 0, 0, 0); Mat tVec1 = (Mat_(3, 1) << 0, 0, 1); /******* pose 2 *******/ Mat rVec2 = (Mat_(3, 1) << 0.0, 0.0, 0); Mat tVec2 = (Mat_(3, 1) << 0.2, 0, 1); // 2nd camera pose is just a pose1 translated by 0.2 along the X axis int iterCount = 50; int N = 40; for (int j = 0; j < iterCount; j++) { /******* generate 3D points *******/ vector points3d = generatePlanarPoints(N); /******* project 3D points from pose 1 *******/ vector points2d1; projectPoints(points3d, rVec1, tVec1, camMat, distCoeffs, points2d1); /******* project 3D points from pose 2 *******/ vector points2d2; projectPoints(points3d, rVec2, tVec2, camMat, distCoeffs, points2d2); /******* add noise to 2D points *******/ std::default_random_engine generator; double noise = 1.0 / 640; if (noise > 0.0) { std::normal_distribution distribution(0.0, noise); for (int i = 0; i < N; i++) { points2d1[i].x += distribution(generator); points2d1[i].y += distribution(generator); points2d2[i].x += distribution(generator); points2d2[i].y += distribution(generator); } } /******* find transformation from 2D - 2D correspondences *******/ double threshold = 2.0 / 640; Mat essentialMat = findEssentialMat(points2d1, points2d2, 1.0, Point(0,0), RANSAC, 0.999, threshold); Mat estimatedRMat1, estimatedRMat2, estimatedTVec; decomposeEssentialMat(essentialMat, estimatedRMat1, estimatedRMat2, estimatedTVec); Mat estimatedRVec1, estimatedRVec2; Rodrigues(estimatedRMat1, estimatedRVec1); Rodrigues(estimatedRMat2, estimatedRVec2); double minError = min(norm(estimatedRVec1 - rVec2), norm(estimatedRVec2 - rVec2)); log << minError << endl; // logging errors } log.flush(); log.close(); return; } The points are generated like this: vector generatePlanarPoints(int N) { float span = 5.0; vector points3d; for (int i = 0; i < N; i++) { float x = ((float)rand() / RAND_MAX - 0.5) * span; float y = ((float)rand() / RAND_MAX - 0.5) * span; float z = 0; Point3f point3d(x,y,z); points3d.push_back(point3d); } return points3d; } Excerpt from `errorLog.txt` file: 0 0.199337 0.199337 0.199337 0.199338 0 0.199337 0 0 0.199337 0.199337 This shows us that algorithm sometimes performs good (error == 0), and sometimes something weird happens (error == 0.199337). Is there any other explanation for this? Obviously, the algorithm is deterministic and error 0.199337 will appear for a specific configuration of points. What is this configuration, I wasn't able to figure out. I also experimented with different prob and threshold parameters for findEssentialMat. And I tried using more/less points and different camera poses... same thing is happening.

Viewing all articles
Browse latest Browse all 19555

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>