0

私は現在、C ++でopencvライブラリを使用しています。私の目標は、画像の魚眼効果をキャンセルすることです(「平面にする」)関数「undistortImage」を使用して効果をキャンセルしていますが、カメラのキャリブレーションを実行する前に必要ですパラメータK、Knew、およびDを見つけるために、ドキュメントを正確に理解していませんでした(リンク:http://docs.opencv.org/master/db/d58/group__calib3d__fisheye.html#gga37375a2741e88052ce346884dfc9c6a0a0899eaa2f96d6eed9927c4b4f4464e05)。私の理解では、ポイントの 2 つのリストを指定する必要があり、関数「調整」は必要な配列を返すことになっています。だから私の質問は次のとおりです。魚眼画像が与えられた場合、結果を得るためにポイントの2つのリストをどのように選択する必要がありますか? これは当面の私のコードで、非常に基本的なもので、写真を撮って表示し、歪みを補正して新しい画像を表示するだけです。行列の要素はランダムであるため、現在、結果は期待どおりではありません。答えてくれてありがとう。

#include "opencv2\core\core.hpp"
#include "opencv2\highgui\highgui.hpp"
#include "opencv2\calib3d\calib3d.hpp"
#include <stdio.h>
#include <iostream>


using namespace std;
using namespace cv;

int main(){

    cout << " Usage: display_image ImageToLoadAndDisplay" << endl;
    Mat image;
    image = imread("C:/Users/Administrator/Downloads/eiffel.jpg", CV_LOAD_IMAGE_COLOR);   // Read the file
    if (!image.data)                              // Check for invalid input
    {
        cout << "Could not open or find the image" << endl;
        return -1;
    }
    cout << "Input image depth: " << image.depth() << endl;

    namedWindow("Display window", WINDOW_AUTOSIZE);// Create a window for display.
    imshow("Display window", image);                   // Show our image inside it.

    Mat Ka = Mat::eye(3, 3, CV_64F); // Creating distortion matrix
    Mat Da = Mat::ones(1, 4, CV_64F);
    Mat dstImage(image.rows, image.cols, CV_32F);

    cout << "K matrix depth: " << Ka.depth() << endl;
    cout << "D matrix depth: " << Da.depth() << endl;

    Mat Knew = Mat::eye(3, 3, CV_64F);
    std::vector<cv::Vec3d> rvec;
    std::vector<cv::Vec3d> tvec;
    int flag = 0; 
    std::vector<Point3d> objectPoints1 = { Point3d(0,0,0),  Point3d(1,1,0),  Point3d(2,2,0), Point3d(3,3,0), Point3d(4,4,0), Point3d(5,5,0), 
        Point3d(6,6,0),  Point3d(7,7,0),  Point3d(3,0,0), Point3d(4,1,0), Point3d(5,2,0), Point3d(6,3,0), Point3d(7,4,0),  Point3d(8,5,0),  Point3d(5,4,0), Point3d(0,7,0), Point3d(9,7,0), Point3d(9,0,0), Point3d(4,3,0), Point3d(7,2,0)};
    std::vector<Point2d> imagePoints1 = { Point(107,84),  Point(110,90),  Point(116,96), Point(126,107), Point(142,123), Point(168,147),
        Point(202,173),  Point(232,192),  Point(135,69), Point(148,73), Point(165,81), Point(189,93), Point(219,112),  Point(248,133),  Point(166,119), Point(96,183), Point(270,174), Point(226,56), Point(144,102), Point(206,75) };

    std::vector<std::vector<cv::Point2d> > imagePoints(1);
    imagePoints[0] = imagePoints1;
    std::vector<std::vector<cv::Point3d> > objectPoints(1);
    objectPoints[0] = objectPoints1;
    fisheye::calibrate(objectPoints, imagePoints, image.size(), Ka, Da, rvec, tvec, flag); // Calibration
    cout << Ka<< endl;
    cout << Da << endl;
    fisheye::undistortImage(image, dstImage, Ka, Da, Knew); // Performing distortion
    namedWindow("Display window 2", WINDOW_AUTOSIZE);// Create a window for display.
    imshow("Display window 2", dstImage);                   // Show our image inside it.

    waitKey(0);                                          // Wait for a keystroke in the window
    return 0;
}
4

1 に答える 1

1

キャリブレーションにcv::fisheye::calibrateは、提供する必要があります

objectPoints    vector of vectors of calibration pattern points in the calibration pattern coordinate space. 

これは、ポイントの既知の現実世界の座標を提供することを意味します (imagePoints 内のポイントに対応するポイントである必要があります)。ただし、座標系の位置は任意に選択できます (ただし、デカルト座標系)。そのため、オブジェクト (平面テスト パターンなど) を知っている必要があります。 .

imagePoints vector of vectors of the projections of calibration pattern points

これらは objectPoints と同じポイントである必要がありますが、画像座標で指定されるため、オブジェクト ポイントの投影が画像に当たる場所 (画像から座標を読み取り/抽出します)。

たとえば、カメラがこの画像をキャプチャした場合 (ここから取得):

魚眼カメラで撮影したテストパターンの画像

テストパターンの寸法 (スケールまで) を知っている必要があります。たとえば、左上の正方形の左上隅を位置 (0,0,0) に選択できます。 -左の四角が (1,0,0) になり、左上の四角の左下隅が (1,1,0) になるため、テストパターン全体が xy 平面に配置されます。

次に、これらの通信を抽出できます。

pixel        real-world
(144,103)    (4,3,0)
(206,75)     (7,2,0)
(109,151)    (2,5,0)
(253,159)    (8,6,0)

これらのポイント(赤でマーク):

ここに画像の説明を入力

ピクセル位置がimagePointsリストになり、実際の位置がobjectPointsリストになる可能性があります。

これはあなたの質問に答えていますか?

于 2016-02-10T15:11:19.100 に答える