2011-05-16 5 views
8

다음 코드를 사용하여 이미지를 입력합니다. 알 수없는 이유에 대한 결과는 쓰레기입니다! 변형 된 이미지가 "악용 된 별"과 비슷하기 때문에 호모 그래피 매트릭스가 잘못되었습니다 (또는 잘못 영향을받는 것 같습니다) ! 나는 문제의 근원이라고 생각하는 부분을 언급했다. 그러나 나는 그것을 깨닫지 못한다. 도움이나 요점이 적합합니다! OpenCV - Image Stitching

이 좋은 하루 되세요, 알리

void Stitch2Image(IplImage *mImage1, IplImage *mImage2) 
{ 

    // Convert input images to gray 
    IplImage* gray1 = cvCreateImage(cvSize(mImage1->width, mImage1->height), 8, 1); 

    cvCvtColor(mImage1, gray1, CV_BGR2GRAY); 
    IplImage* gray2 = cvCreateImage(cvSize(mImage2->width, mImage2->height), 8, 1); 

    cvCvtColor(mImage2, gray2, CV_BGR2GRAY); 
    // Convert gray images to Mat 
    Mat img1(gray1); 
    Mat img2(gray2); 
    // Detect FAST keypoints and BRIEF features in the first image 
    FastFeatureDetector detector(50); 
    BriefDescriptorExtractor descriptorExtractor; 
    BruteForceMatcher<L1<uchar> > descriptorMatcher; 
    vector<KeyPoint> keypoints1; 
    detector.detect(img1, keypoints1); 
    Mat descriptors1; 
    descriptorExtractor.compute(img1, keypoints1, descriptors1); 

/* Detect FAST keypoints and BRIEF features in the second image*/ 


    vector<KeyPoint> keypoints2; 
    detector.detect(img1, keypoints2); 
    Mat descriptors2; 
    descriptorExtractor.compute(img2, keypoints2, descriptors2); 
    vector<DMatch> matches; 
    descriptorMatcher.match(descriptors1, descriptors2, matches); 
    if (matches.size()==0) 
      return; 
    vector<Point2f> points1, points2; 
    for(size_t q = 0; q < matches.size(); q++) 
    { 
      points1.push_back(keypoints1[matches[q].queryIdx].pt); 
      points2.push_back(keypoints2[matches[q].trainIdx].pt); 
    } 
    // Create the result image 
    result = cvCreateImage(cvSize(mImage2->width * 2, mImage2->height), 8, 3); 
    cvZero(result); 

    // Copy the second image in the result image 

    cvSetImageROI(result, cvRect(mImage2->width, 0, mImage2->width, mImage2->height)); 
    cvCopy(mImage2, result); 
    cvResetImageROI(result); 

    // Create warp image 
    IplImage* warpImage = cvCloneImage(result); 
    cvZero(warpImage); 

    /************************** Is there anything wrong here!? *******************/ 
    // Find homography matrix 
    Mat H = findHomography(Mat(points1), Mat(points2), 8, 3.0); 
    CvMat HH = H; // Is this line converted correctly? 
    // Transform warp image 
    cvWarpPerspective(mImage1, warpImage, &HH); 
    // Blend 
    blend(result, warpImage); 
    /*******************************************************************************/ 

    cvReleaseImage(&gray1); 
    cvReleaseImage(&gray2); 
    cvReleaseImage(&warpImage); 
} 

답변

7

이 나는 ​​순서대로, 당신이 시도하는 것이 좋습니다 것 인 것이다 : 호모 그래피에 대한

1) 사용 CV_RANSAC 옵션을 선택합니다. http://opencv.willowgarage.com/documentation/cpp/calib3d_camera_calibration_and_3d_reconstruction.html

2) 다른 설명자, 특히 OpenCV와 함께 제공되는 SIFT 또는 SURF를 사용해보십시오. 일부 이미지의 경우 FAST 또는 BRIEF 디스크립터는 충분히 차별화되지 않습니다. EDIT (Aug 12) : BRIEF를 기반으로하는 ORB 디스크립터는 매우 훌륭하고 빠르다.

3) 호모 그래피 매트릭스 (디버그 모드에서 단계별 또는 인쇄)를보고 일관성이 있는지 확인하십시오.

4) 위의 경우 단서가 주어지지 않으면 형성되는 일치를 살펴보십시오. 한 이미지의 한 점과 다른 이미지의 점이 일치합니까? 그렇다면 문제는 다시 설명자 또는 탐지기와 함께 있어야합니다.

내 직감은 설명자 (1) 또는 2)가 수정해야한다는 것입니다.)

+0

안녕하세요, tanx 님의 답변입니다. – Edi

+1

어떤 제안이 효과가 있습니까? – Muzikant

1

귀하의 동질성은 잘못된 성냥을 기반으로 계산 될 수 있으므로 잘못된 할당을 나타낼 수 있습니다. 행 사이의 상호 의존성에 대한 추가 검사를 통해 행렬을 경로 지정하는 것이 좋습니다.

bool cvExtCheckTransformValid(const Mat& T){ 

    // Check the shape of the matrix 
    if (T.empty()) 
     return false; 
    if (T.rows != 3) 
     return false; 
    if (T.cols != 3) 
     return false; 

    // Check for linear dependency. 
    Mat tmp; 
    T.row(0).copyTo(tmp); 
    tmp /= T.row(1); 
    Scalar mean; 
    Scalar stddev; 
    meanStdDev(tmp,mean,stddev); 
    double X = abs(stddev[0]/mean[0]); 
    printf("std of H:%g\n",X); 
    if (X < 0.8) 
     return false; 

    return true;  
} 
2

는 또한 BruteForceMatcher의 해밍 거리 대신 L1 거리로 전환 :

는 다음과 같은 코드를 사용할 수 있습니다. 간략한 설명자는 해밍 거리를 사용하여 비교되어야합니다.