使用两个图像找到相机旋转

时间:2016-09-23 11:57:11

标签: java opencv computer-vision

更新

我有一架 GoPro Hero4 Black 安装在接收无人机遥测的无人机上,有时往往不准确。我需要通过计算相机的两个不同帧的旋转和平移来验证遥测。

我使用内部参数计算了基本矩阵,这是我从相机矩阵中提取的,我已经通过 OpenCV 获得了这些参数棋盘校准。

问题 现在我得到的结果是垃圾,除非我将相同的照片与自身进行比较。它们也根据我使用的功能检测器或我是否使用 RANSAC LMEDS 而有所不同,但我很确定关键点匹配本身效果很好。所以我相信我

要么 会分解基本矩阵并错误地检索其对应的角度

即使重投影误差为0.23,我的相机校准也不好。

但是,我不知道如何验证它们中的哪一个是真的(或者如果有的话)。我找到了基本矩阵分解的其他方法,比如这个Decomposition of Essential Matrix: Validation of the four possible solutions for R and T,我不知道这种方法和我的方法有什么区别 - 使用 org.opencv.calib3d .Calib3d.decomposeEssentialMat(..)。有人在意澄清吗?

问题1:有人可以检查我的角度检索是否正确吗?

问题2:我不知道如何检查我的相机校准是否正确但是我在下面发布它以及 Calib3d.calibrationMatrixValues(..)检索的参数。我认为这不是因为检索到的视野与我的相机规格不同。你能证实一下吗?

我正在使用 Java OpenCV 3.1

感谢您的帮助。

主要功能

        // Match keypoints
        // ....
        MatOfPoint2f firstImageMop2f = new MatOfPoint2f();
        firstImageMop2f.fromList(firstImageList);

        MatOfPoint2f secondImageMop2f = new MatOfPoint2f();
        secondImageMop2f.fromList(secondImageList);

        Mat essentialMat = org.opencv.calib3d.Calib3d.findEssentialMat(firstImageMop2f, secondImageMop2f,
                3.5714310113232735, new Point(3.1427346523449033, 2.383214663142159),
                org.opencv.calib3d.Calib3d.RANSAC, 0.999, 3);
        decomposeEssential(essentialMat);

分解必要

private void decomposeEssential(Mat essentialMat) {
    Mat firstRotation = new Mat();
    Mat secondRotation = new Mat();
    Mat translation = new Mat();
    org.opencv.calib3d.Calib3d.decomposeEssentialMat(essentialMat, firstRotation, secondRotation, translation);
    printRotationMatrix(firstRotation, "Rotation matrix");
    printRotationMatrix(secondRotation, "Rotation matrix");
    printGeneralMatrix(translation, "Translation");
}

打印旋转矩阵

private void printRotationMatrix(Mat matrix, String description) {
    double x, y, z;
    double sy = Math.sqrt(matrix.get(0, 0)[0] * matrix.get(0, 0)[0]
                            + matrix.get(1, 0)[0] * matrix.get(1, 0)[0]);
    boolean singular = sy < 1e-6;

    if (!singular) {
        System.out.println(" as a non singular matrix");
        x = Math.atan2(matrix.get(2, 1)[0], matrix.get(2, 2)[0]); //roll
        y = Math.atan2(-matrix.get(2, 0)[0], sy); // pitch
        z = Math.atan2(matrix.get(1, 0)[0], matrix.get(0, 0)[0]); // yaw
    } else {
        System.out.println(" as a singular matrix");
        x = Math.atan2(-matrix.get(2, 1)[0], matrix.get(2, 2)[0]);
        y = Math.atan2(-matrix.get(2, 0)[0], sy);
        z = 0;
    }

    System.out.println("Axes angles: ");
    System.out.println("x (roll): " + Math.toDegrees(x));
    System.out.println("y (pitch): " + Math.toDegrees(y));
    System.out.println("z (yaw): " + Math.toDegrees(z));
}

相机矩阵

    740.9127543750064 0.0 651.9773670991048 
    0.0 736.5104868078901 377.12407856315485 
    0.0 0.0 1.0 

Calib3d.calibrationMatrixValues(cameraMatrix,新尺寸(1280,720),6.17,4.55,输出参数......)

    FoVx: 81.64086856941297
    FoVy: 52.09797490556325
    Focal length: 3.5714310113232735
    Principal point of view; x: 3.1427346523449033, y: 2.383214663142159
    Aspect ratio: 0.9940583185521892

0 个答案:

没有答案