OpenCV стерео карта глубины зрения, код не работает

Я изучаю карту глубины стереозрения и использую библиотеку opencv. Я написал программу для получения карты глубины. Но когда программа была запущена, я получил пустой фрейм карты глубины. Кто-нибудь может мне помочь, пожалуйста, что не так? код показан ниже;

#include <opencv/highgui.h>
#include <opencv/cv.h>
#include <stdio.h>
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <math.h>
#include <opencv2/calib3d/calib3d.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/contrib/contrib.hpp>
int main()
{
IplImage* img1 = cvLoadImage("/home/sezen/Masaüstü/imR.png");
IplImage* img2 = cvLoadImage("/home/sezen/Masaüstü/imL.png");

IplImage *rimage = cvCreateImage(
cvSize( img1->width, img1->height ), IPL_DEPTH_8U, 1 );
cvCvtColor( img1, rimage, CV_RGB2GRAY );

IplImage *limage = cvCreateImage(
cvSize( img2->width, img2->height ), IPL_DEPTH_8U, 1 );
cvCvtColor( img2, limage, CV_RGB2GRAY );

cvNamedWindow( "Right", CV_WINDOW_AUTOSIZE );
cvShowImage( "Right", rimage );

cvNamedWindow( "Left", CV_WINDOW_AUTOSIZE );
cvShowImage("Left", limage);

CvMat *matr = cvCreateMat(rimage->height,rimage->width,CV_8UC1 );
CvMat *matl = cvCreateMat(limage->height,limage->width,CV_8UC1 );
CvMat* disp = cvCreateMat(rimage->height,rimage->width,CV_16S);
CvMat* vdisp = cvCreateMat(rimage->height,rimage->width,CV_16S);

cvConvert( rimage, matr );
cvConvert( limage, matl );

CvStereoBMState *BMState = cvCreateStereoBMState();
assert(BMState != 0);
BMState->preFilterSize=21;
BMState->preFilterCap=31;
BMState->SADWindowSize=21;
BMState->minDisparity=0;
BMState->numberOfDisparities=128;
BMState->textureThreshold=10;
BMState->uniquenessRatio=15;cvFindStereoCorrespondenceBM( matr, matl, disp, BMState);
cvNormalize(disp, vdisp, 0, 255, CV_MINMAX);

cvShowImage("depthmap", vdisp);
cvWaitKey(0);
return 0;
}

4

Решение

Вот код для отображения несоответствия с использованием C ++ API. Конечное изображение, которое вы нормализуете, должно иметь тип CV_8UC1.

Mat img1, img2, g1, g2;
Mat disp, disp8;

img1 = imread("leftImage.jpg");
img2 = imread("rightImage.jpg");

cvtColor(img1, g1, CV_BGR2GRAY);
cvtColor(img2, g2, CV_BGR2GRAY);

StereoBM sbm;
sbm.state->SADWindowSize = 9;
sbm.state->numberOfDisparities = 112;
sbm.state->preFilterSize = 5;
sbm.state->preFilterCap = 61;
sbm.state->minDisparity = -39;
sbm.state->textureThreshold = 507;
sbm.state->uniquenessRatio = 0;
sbm.state->speckleWindowSize = 0;
sbm.state->speckleRange = 8;
sbm.state->disp12MaxDiff = 1;

sbm(g1, g2, disp);
normalize(disp, disp8, 0, 255, CV_MINMAX, CV_8U);

imshow("left", img1);
imshow("right", img2);
imshow("disp", disp8);
3

Другие решения

Я могу только добавить, что структура пространств имен и классов OpenCV меняется каждый год.
Я поместил ниже рабочий исходный код для OpenCV 3.4.0

#include <Windows.h>
#include <Vfw.h>
#include <string>
#include <iostream>#include "opencv2\core\core.hpp"#include "opencv2\imgproc\imgproc.hpp"#include "opencv2\imgcodecs\imgcodecs.hpp"#include "opencv2\highgui\highgui.hpp"#include "opencv2\calib3d\calib3d.hpp"
using namespace std;
using namespace cv;int _tmain(int argc, _TCHAR* argv[])
{
Mat im_left=imread("right.png");
Mat im_right=imread("left.png");
cv::Size imagesize = im_left.size();
cv::Mat disparity_left=cv::Mat(imagesize.height,imagesize.width,CV_16S);
cv::Mat disparity_right=cv::Mat(imagesize.height,imagesize.width,CV_16S);
cv::Mat g1,g2,disp,disp8;
cv::cvtColor(im_left,g1,cv::COLOR_BGR2GRAY);
cv::cvtColor(im_right,g2,cv::COLOR_BGR2GRAY);
cv::Ptr<cv::StereoBM> sbm = cv::StereoBM::create(0,21);
sbm->setDisp12MaxDiff(1);
sbm->setSpeckleRange(8);
sbm->setSpeckleWindowSize(9);
sbm->setUniquenessRatio(0);
sbm->setTextureThreshold(507);
sbm->setMinDisparity(-39);
sbm->setPreFilterCap(61);
sbm->setPreFilterSize(5);
sbm->compute(g1,g2,disparity_left);
normalize(disparity_left, disp8, 0, 255, CV_MINMAX, CV_8U);
cv::namedWindow("Left",CV_WINDOW_FREERATIO);
cv::imshow("Left", im_left);
cv::namedWindow("Right",CV_WINDOW_FREERATIO);
cv::imshow("Right", im_right);
cv::namedWindow("Depth map",CV_WINDOW_FREERATIO);
cv::imshow("Depth map", disp8);
cv::waitKey(0);
return 0;
}
2

Для меня это работало немного иначе с инициализацией объекта стереоБМ

Ptr<StereoBM> sbm = cv::StereoBM::create(16, 5);

sbm->setDisp12MaxDiff(1);
sbm->setSpeckleRange(8);
sbm->setSpeckleWindowSize(0);
sbm->setUniquenessRatio(0);
sbm->setTextureThreshold(507);
sbm->setMinDisparity(-39);
sbm->setPreFilterCap(61);
sbm->setPreFilterSize(5);
sbm->compute(src1, src2, disp);
1

#include <opencv2/opencv.hpp>
#include <opencv2/highgui.hpp>
#include<opencv2/calib3d.hpp>
int main()
{
cv::Mat leftimg =cv::imread("leftimage.jpg");
cv::Mat rightimg = cv::imread("rightimage.jpg");
cv::Mat disparity_left=cv::Mat(leftimg.size(),leftimg.type());
cv::Mat disparity_right=cv::Mat(rightimg.size(),rightimg .type());
cv::Mat g1,g2,disp,disp8;
cv::cvtColor(leftimg,g1,cv::COLOR_BGR2GRAY);
cv::cvtColor(rightimg,g2,cv::COLOR_BGR2GRAY);

cv::Ptr<cv::StereoBM> sbm = cv::createStereoBM(16,21);sbm->setDisp12MaxDiff(1);
sbm->setSpeckleRange(8);
sbm->setSpeckleWindowSize(9);
sbm->setUniquenessRatio(0);
sbm->setTextureThreshold(507);
sbm->setMinDisparity(-39);
sbm->setPreFilterCap(61);
sbm->setPreFilterSize(5);
sbm->compute(g1,g2,disparity_left);
normalize(disparity_left, disp8, 0, 255, CV_MINMAX, CV_8U);

}
0

Я отредактировал код под свои нужды, добавил камеры один и два и начал читать с них.
Затем сделал карту глубины. Спасибо, надеюсь, это полезно.

#include <string>
#include <iostream>
#include <opencv2/opencv.hpp>
#include "opencv2/core/core.hpp"#include "opencv2/imgproc/imgproc.hpp"#include "opencv2/imgcodecs/imgcodecs.hpp"#include "opencv2/highgui/highgui.hpp"#include "opencv2/calib3d/calib3d.hpp"
using namespace std;
using namespace cv;

int main()
{
VideoCapture leftCam(0);      //lets say 0 is left, 1 is right
if (leftCam.isOpened() == false){cout << "error: Webcam connect unsuccessful\n";    return(0);    }
VideoCapture rightCam(1);     //lets say 0 is left, 1 is right
if (rightCam.isOpened() == false){cout << "error: Webcam connect unsuccessful\n";   return(0);    }
Mat left, right;
Mat leftClone, rightClone;

char charCheckForEscKey = 0;

while (    charCheckForEscKey != 27 && leftCam.isOpened()  )
{

leftCam.read(left);
if (left.empty()){cout << "No frame to read" << endl;  break;}
leftClone = left.clone();               //copy from the left camera
imwrite("left.png", leftClone);         // write it to screenshot.png in this directory

rightCam.read(right);
if (right.empty()){cout << "No frame to read" << endl;  break;}
rightClone = right.clone();             //copy from the left camera
imwrite("right.png", rightClone);           // write it to screenshot.png in this directory

Mat im_left = imread("left.png"); //left cam picture
Mat im_right = imread("right.png"); // right cam  picture

Size imagesize = im_left.size();
Mat disparity_left= Mat(imagesize.height,imagesize.width,CV_16S);
Mat disparity_right=Mat(imagesize.height,imagesize.width,CV_16S);
Mat g1,g2,disp,disp8;
cvtColor(im_left,g1, COLOR_BGR2GRAY);
cvtColor(im_right,g2, COLOR_BGR2GRAY);

Ptr<cv::StereoBM> sbm =  StereoBM::create(0,21);

sbm->setDisp12MaxDiff(1);
sbm->setSpeckleRange(8);
sbm->setSpeckleWindowSize(9);
sbm->setUniquenessRatio(0);
sbm->setTextureThreshold(507);
sbm->setMinDisparity(-39);
sbm->setPreFilterCap(61);
sbm->setPreFilterSize(5);
sbm->compute(g1,g2,disparity_left);

normalize(disparity_left, disp8, 0, 255, NORM_MINMAX, CV_8U);
namedWindow("Left", WINDOW_AUTOSIZE);
imshow("Left", im_left);

namedWindow("Right", WINDOW_AUTOSIZE);
imshow("Right", im_right);
namedWindow("Depth map", WINDOW_AUTOSIZE);
imshow("Depth map", disp8);

namedWindow("Left Cloned", WINDOW_FREERATIO);
imshow("Left Cloned", leftClone);   // left is the left pic taken from camera 0

charCheckForEscKey = waitKey(1);
}

return(0);

}

0
По вопросам рекламы ammmcru@yandex.ru
Adblock
detector