Skip to content

Commit df85952

Browse files
committed
made modifications in accordance to the comments
fixed that unused variable warning fixed windows warnings Added 2 samples just to show how to access functionality fixed issues added the up to date version of sbm modified samples to be warning free
1 parent 54d4125 commit df85952

File tree

7 files changed

+528
-573
lines changed

7 files changed

+528
-573
lines changed

modules/stereo/include/opencv2/stereo.hpp

Lines changed: 216 additions & 198 deletions
Large diffs are not rendered by default.

modules/stereo/samples/Sample1.cpp

Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
#include <iostream>
2+
#include "opencv2/stereo.hpp"
3+
#include "opencv2/imgproc.hpp"
4+
#include "opencv2/highgui.hpp"
5+
#include <iostream>
6+
7+
using namespace cv;
8+
using namespace stereo;
9+
using namespace std;
10+
11+
//in this example we will load a sequence of images from a file process them and display the result on the screen
12+
//the descriptor used is the modified_census transform
13+
14+
int main(int, char**)
15+
{
16+
//begin the program
17+
cout << " Running Main function \n";
18+
//declare 2 images
19+
Mat image1, image2;
20+
21+
// -- 1. Call the constructor for StereoBinaryBM
22+
int ndisparities = 32; /**< Range of disparity */
23+
int kernelSize = 9; /**< Size of the block window. Must be odd */
24+
25+
Ptr<StereoBinaryBM> sbm = StereoBinaryBM::create(ndisparities, kernelSize);
26+
27+
// -- 2. Set parameters
28+
sbm->setPreFilterCap(31);
29+
sbm->setMinDisparity(0);
30+
sbm->setTextureThreshold(10);
31+
sbm->setUniquenessRatio(0);
32+
sbm->setSpeckleWindowSize(400);//speckle size
33+
sbm->setSpeckleRange(200);
34+
sbm->setDisp12MaxDiff(0);
35+
sbm->setScalleFactor(4);//the scalling factor
36+
sbm->setBinaryKernelType(CV_MODIFIED_CENSUS_TRANSFORM);//binary descriptor kernel
37+
sbm->setAgregationWindowSize(9);
38+
sbm->setSpekleRemovalTechnique(CV_SPECKLE_REMOVAL_AVG_ALGORITHM);//speckle removal algorithm
39+
sbm->setUsePrefilter(false);//prefilter or not the images prior to making the transformations
40+
41+
for(int i = 0 ; i < 200; i++)
42+
{
43+
string path = "D:\\WorkingSec";
44+
string left = "l.bmp";
45+
string right = ".bmp";
46+
47+
std::string s;
48+
std::stringstream out;
49+
out << i;
50+
s = out.str();
51+
52+
string finLeft = path + "\\rezult" + s + left;
53+
string finRigth = path + "\\rezult" + s + right;
54+
55+
image1 = imread(finLeft, CV_8UC1);
56+
image2 = imread(finRigth, CV_8UC1);
57+
//set a certain region of interest
58+
Rect region_of_interest = Rect(0, 20, image1.cols, (image1.rows - 20 - 110));
59+
60+
Mat imgLeft = image1(region_of_interest);
61+
Mat imgRight = image2(region_of_interest);
62+
63+
Mat imgDisparity8U = Mat(imgLeft.rows, imgLeft.cols, CV_8UC1);
64+
if (imgLeft.empty() || imgRight.empty())
65+
{
66+
std::cout << " --(!) Error reading images \n" ; return -1;
67+
}
68+
////-- 3. Calculate the disparity image
69+
sbm->compute(imgLeft, imgRight, imgDisparity8U);
70+
71+
imshow("RealImage", image1);
72+
imshow("Disparity", imgDisparity8U);
73+
waitKey(1);
74+
}
75+
76+
waitKey(0);
77+
return 0;
78+
}

modules/stereo/samples/Sample2.cpp

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
#include <iostream>
2+
#include "opencv2/stereo.hpp"
3+
#include "opencv2/imgproc.hpp"
4+
#include "opencv2/highgui.hpp"
5+
#include <iostream>
6+
7+
using namespace cv;
8+
using namespace stereo;
9+
using namespace std;
10+
11+
12+
int main(int, char**)
13+
{
14+
//begin the program
15+
cout << " Running Main function \n";
16+
//declare 2 images
17+
Mat image1, image2;
18+
19+
// -- 1. Call the constructor for StereoBinaryBM
20+
int ndisparities = 32; /**< Range of disparity */
21+
int kernelSize = 9; /**< Size of the block window. Must be odd */
22+
23+
Ptr<StereoBinaryBM> sbm = StereoBinaryBM::create(ndisparities, kernelSize);
24+
25+
// -- 2. Set parameters
26+
sbm->setPreFilterCap(31);
27+
sbm->setMinDisparity(0);
28+
sbm->setTextureThreshold(10);
29+
sbm->setUniquenessRatio(0);
30+
sbm->setSpeckleWindowSize(400);//speckle size
31+
sbm->setSpeckleRange(200);
32+
sbm->setDisp12MaxDiff(0);
33+
sbm->setScalleFactor(4);//the scalling factor
34+
sbm->setBinaryKernelType(CV_MEAN_VARIATION);//binary descriptor kernel
35+
sbm->setAgregationWindowSize(9);
36+
sbm->setSpekleRemovalTechnique(CV_SPECKLE_REMOVAL_AVG_ALGORITHM);//speckle removal algorithm
37+
sbm->setUsePrefilter(false);//prefilter or not the images prior to making the transformations
38+
39+
//load 2 images from disc
40+
image1 = imread("D:\\rezult0l.bmp", CV_8UC1);
41+
image2 = imread("D:\\rezult0.bmp", CV_8UC1);
42+
//set a certain region of interest
43+
Rect region_of_interest = Rect(0, 20, image1.cols, (image1.rows - 20 - 110));
44+
45+
Mat imgLeft = image1(region_of_interest);
46+
Mat imgRight = image2(region_of_interest);
47+
48+
Mat imgDisparity8U = Mat(imgLeft.rows, imgLeft.cols, CV_8UC1);
49+
if (imgLeft.empty() || imgRight.empty())
50+
{
51+
std::cout << " --(!) Error reading images \n" ; return -1;
52+
}
53+
////-- 3. Calculate the disparity image
54+
sbm->compute(imgLeft, imgRight, imgDisparity8U);
55+
56+
imshow("RealImage", image1);
57+
imshow("Disparity", imgDisparity8U);
58+
59+
waitKey(0);
60+
return 0;
61+
}

modules/stereo/src/descriptor.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ namespace cv
5858
enum {
5959
CV_DENSE_CENSUS, CV_SPARSE_CENSUS,
6060
CV_CS_CENSUS, CV_MODIFIED_CS_CENSUS, CV_MODIFIED_CENSUS_TRANSFORM,
61-
CV_MEAN_VARIATION
61+
CV_MEAN_VARIATION, CV_STAR_KERNEL
6262
};
6363
//!Mean Variation is a robust kernel that compares a pixel
6464
//!not just with the center but also with the mean of the window

modules/stereo/src/matching.cpp

Lines changed: 28 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -57,14 +57,12 @@ namespace cv
5757
//maxDisp - represents the maximum disparity
5858
Matching::Matching(int maxDisp, int scalling, int confidence)
5959
{
60-
CV_Assert(maxDisp > 10);
61-
CV_Assert(scalling != 0);
62-
CV_Assert(confidence >= 1);
63-
this->scallingFactor = scalling;
6460
//set the maximum disparity
65-
this->maxDisparity = maxDisp;
61+
setMaxDisparity(maxDisp);
62+
//set scalling factor
63+
setScallingFactor(scalling);
6664
//set the value for the confidence
67-
this->confidenceCheck = confidence;
65+
setConfidence(confidence);
6866
//generate the hamming lut in case SSE is not available
6967
hammingLut();
7068
}
@@ -82,7 +80,7 @@ namespace cv
8280
void Matching::setScallingFactor(int val)
8381
{
8482
CV_Assert(val > 0);
85-
scallingFactor = val;
83+
this->scallingFactor = val;
8684
}
8785
//!method for getting the scalling factor
8886
int Matching::getScallingFactor()
@@ -99,23 +97,23 @@ namespace cv
9997
CV_Assert(kernelSize % 2 != 0);
10098
CV_Assert(cost.rows == leftImage.rows);
10199
CV_Assert(cost.cols / (maxDisparity + 1) == leftImage.cols);
102-
// cost.setTo(0);
103-
int *c = (int *)cost.data;
104-
memset(c, 0, sizeof(c[0]) * leftImage.cols * leftImage.rows * (maxDisparity + 1));
105-
parallel_for_(cv::Range(kernelSize / 2,leftImage.rows - kernelSize / 2), hammingDistance(leftImage,rightImage,c,maxDisparity,kernelSize / 2,hamLut));
100+
cost.setTo(0);
101+
//int *c = (int *)cost.data;
102+
//memset(c, 0, sizeof(c[0]) * leftImage.cols * leftImage.rows * (maxDisparity + 1));
103+
parallel_for_(cv::Range(kernelSize / 2,leftImage.rows - kernelSize / 2), hammingDistance(leftImage,rightImage,(int *)cost.data,maxDisparity,kernelSize / 2,hamLut));
106104
}
107105
//preprocessing the cost volume in order to get it ready for aggregation
108106
void Matching::costGathering(const Mat &hammingDistanceCost, Mat &cost)
109107
{
110108
CV_Assert(hammingDistanceCost.rows == hammingDistanceCost.rows);
111109
CV_Assert(hammingDistanceCost.type() == CV_32SC4);
112110
CV_Assert(cost.type() == CV_32SC4);
113-
//cost.setTo(0);
111+
cost.setTo(0);
114112
int maxDisp = maxDisparity;
115113
int width = cost.cols / ( maxDisp + 1) - 1;
116114
int height = cost.rows - 1;
117115
int *c = (int *)cost.data;
118-
memset(c, 0, sizeof(c[0]) * (width + 1) * (height + 1) * (maxDisp + 1));
116+
//memset(c, 0, sizeof(c[0]) * (width + 1) * (height + 1) * (maxDisp + 1));
119117
parallel_for_(cv::Range(1,height), costGatheringHorizontal(hammingDistanceCost,maxDisparity,cost));
120118
for (int i = 1; i <= height; i++)
121119
{
@@ -136,12 +134,13 @@ namespace cv
136134
CV_Assert(windowSize % 2 != 0);
137135
CV_Assert(partialSums.rows == cost.rows);
138136
CV_Assert(partialSums.cols == cost.cols);
137+
cost.setTo(0);
139138
int win = windowSize / 2;
140-
int *c = (int *)cost.data;
139+
//int *c = (int *)cost.data;
141140
int maxDisp = maxDisparity;
142-
int width = cost.cols / ( maxDisp + 1) - 1;
141+
//int width = cost.cols / ( maxDisp + 1) - 1;
143142
int height = cost.rows - 1;
144-
memset(c, 0, sizeof(c[0]) * width * height * (maxDisp + 1));
143+
//memset(c, 0, sizeof(c[0]) * width * height * (maxDisp + 1));
145144
parallel_for_(cv::Range(win + 1,height - win - 1), agregateCost(partialSums,windowSize,maxDisp,cost));
146145
}
147146
//!Finding the correct disparity from the cost volume, we also make a confidence check
@@ -303,7 +302,7 @@ namespace cv
303302
void Matching ::setConfidence(double val)
304303
{
305304
CV_Assert(val >= 1);
306-
confidenceCheck = val;
305+
this->confidenceCheck = val;
307306
}
308307
//getter for confidence check
309308
double Matching ::getConfidence()
@@ -313,26 +312,27 @@ namespace cv
313312
//!Method responsible for generating the disparity map
314313
void Matching::dispartyMapFormation(const Mat &costVolume, Mat &mapFinal, int th)
315314
{
316-
uint8_t *map = mapFinal.data;
315+
mapFinal.setTo(0);
316+
//uint8_t *map = mapFinal.data;
317317
int disparity = maxDisparity;
318-
int width = costVolume.cols / ( disparity + 1) - 1;
318+
//int width = costVolume.cols / ( disparity + 1) - 1;
319319
int height = costVolume.rows - 1;
320-
memset(map, 0, sizeof(map[0]) * width * height);
320+
//memset(map, 0, sizeof(map[0]) * width * height);
321321
parallel_for_(Range(0,height - 1), makeMap(costVolume,th,disparity,confidenceCheck,scallingFactor,mapFinal));
322322
}
323323
//!1x9 median filter
324-
void Matching::Median1x9Filter(const Mat &originalMap, Mat &map)
324+
void Matching::Median1x9Filter(const Mat &originalImage, Mat &filteredImage)
325325
{
326-
CV_Assert(originalMap.rows == map.rows);
327-
CV_Assert(originalMap.cols == map.cols);
328-
parallel_for_(Range(1,originalMap.rows - 2), Median1x9(originalMap,map));
326+
CV_Assert(originalImage.rows == filteredImage.rows);
327+
CV_Assert(originalImage.cols == filteredImage.cols);
328+
parallel_for_(Range(1,originalImage.rows - 2), Median1x9(originalImage,filteredImage));
329329
}
330330
//!9x1 median filter
331-
void Matching::Median9x1Filter(const Mat &originalMap, Mat &map)
331+
void Matching::Median9x1Filter(const Mat &originalImage, Mat &filteredImage)
332332
{
333-
CV_Assert(originalMap.cols == map.cols);
334-
CV_Assert(originalMap.cols == map.cols);
335-
parallel_for_(Range(1,originalMap.cols - 2), Median9x1(originalMap,map));
333+
CV_Assert(originalImage.cols == filteredImage.cols);
334+
CV_Assert(originalImage.cols == filteredImage.cols);
335+
parallel_for_(Range(1,originalImage.cols - 2), Median9x1(originalImage,filteredImage));
336336
}
337337
}
338338
}

modules/stereo/src/matching.hpp

Lines changed: 29 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -81,12 +81,12 @@ namespace cv
8181
{
8282
private:
8383
int *left, *right, *c;
84-
int v,kernelSize, width, height;
84+
int v,kernelSize, width, height,_stride;
8585
int MASK;
8686
int *hammLut;
8787
public :
8888
hammingDistance(const Mat &leftImage, const Mat &rightImage, int *cost, int maxDisp, int kerSize, int *hammingLUT):
89-
left((int *)leftImage.data), right((int *)rightImage.data), c(cost), v(maxDisp),kernelSize(kerSize),width(leftImage.cols), height(leftImage.rows), MASK(65535), hammLut(hammingLUT){}
89+
left((int *)leftImage.data), right((int *)rightImage.data), c(cost), v(maxDisp),kernelSize(kerSize),width(leftImage.cols), height(leftImage.rows), _stride((int)leftImage.step1()), MASK(65535), hammLut(hammingLUT){}
9090
void operator()(const cv::Range &r) const {
9191
for (int i = r.start; i <= r.end ; i++)
9292
{
@@ -246,16 +246,17 @@ namespace cv
246246
class Median1x9:public ParallelLoopBody
247247
{
248248
private:
249-
uint8_t *harta;
250-
uint8_t *mapModified;
251-
int height, width;
249+
uint8_t *original;
250+
uint8_t *filtered;
251+
int height, width,_stride;
252252
public:
253-
Median1x9(const Mat &hartaOriginala, Mat &map)
253+
Median1x9(const Mat &originalImage, Mat &filteredImage)
254254
{
255-
harta = hartaOriginala.data;
256-
mapModified = map.data;
257-
height = hartaOriginala.rows;
258-
width = hartaOriginala.cols;
255+
original = originalImage.data;
256+
filtered = filteredImage.data;
257+
height = originalImage.rows;
258+
width = originalImage.cols;
259+
_stride = (int)originalImage.step;
259260
}
260261
void operator()(const cv::Range &r) const{
261262
for (int m = r.start; m <= r.end; m++)
@@ -265,7 +266,7 @@ namespace cv
265266
int k = 0;
266267
uint8_t window[9];
267268
for (int i = n - 4; i <= n + 4; ++i)
268-
window[k++] = harta[m * width + i];
269+
window[k++] = original[m * _stride + i];
269270
for (int j = 0; j < 5; ++j)
270271
{
271272
int min = j;
@@ -276,7 +277,7 @@ namespace cv
276277
window[j] = window[min];
277278
window[min] = temp;
278279
}
279-
mapModified[m * width + n] = window[4];
280+
filtered[m * _stride + n] = window[4];
280281
}
281282
}
282283
}
@@ -285,16 +286,17 @@ namespace cv
285286
class Median9x1:public ParallelLoopBody
286287
{
287288
private:
288-
uint8_t *harta;
289-
uint8_t *mapModified;
290-
int height, width;
289+
uint8_t *original;
290+
uint8_t *filtered;
291+
int height, width, _stride;
291292
public:
292-
Median9x1(const Mat &hartaOriginala, Mat &map)
293+
Median9x1(const Mat &originalImage, Mat &filteredImage)
293294
{
294-
harta = hartaOriginala.data;
295-
mapModified = map.data;
296-
height = hartaOriginala.rows;
297-
width = hartaOriginala.cols;
295+
original = originalImage.data;
296+
filtered = filteredImage.data;
297+
height = originalImage.rows;
298+
width = originalImage.cols;
299+
_stride = (int)originalImage.step;
298300
}
299301
void operator()(const Range &r) const{
300302
for (int n = r.start; n <= r.end; ++n)
@@ -304,7 +306,7 @@ namespace cv
304306
int k = 0;
305307
uint8_t window[9];
306308
for (int i = m - 4; i <= m + 4; ++i)
307-
window[k++] = harta[i * width + n];
309+
window[k++] = original[i * _stride + n];
308310
for (int j = 0; j < 5; j++)
309311
{
310312
int min = j;
@@ -315,12 +317,12 @@ namespace cv
315317
window[j] = window[min];
316318
window[min] = temp;
317319
}
318-
mapModified[m * width + n] = window[4];
320+
filtered[m * _stride + n] = window[4];
319321
}
320322
}
321323
}
322324
};
323-
public:
325+
protected:
324326
//!method for setting the maximum disparity
325327
void setMaxDisparity(int val);
326328
//!method for getting the disparity
@@ -347,12 +349,13 @@ namespace cv
347349
*th - is the LR threshold
348350
*/
349351
void dispartyMapFormation(const Mat &costVolume, Mat &map, int th);
352+
void smallRegionRemoval(const Mat &input, int t, Mat &out);
353+
public:
354+
static void Median1x9Filter(const Mat &inputImage, Mat &outputImage);
355+
static void Median9x1Filter(const Mat &inputImage, Mat &outputImage);
350356
//!constructor for the matching class
351357
//!maxDisp - represents the maximum disparity
352358
//!a median filter that has proven to work a bit better especially when applied on disparity maps
353-
static void Median1x9Filter(const Mat &hartaOriginala, Mat &map);
354-
static void Median9x1Filter(const Mat &hartaOriginala, Mat &map);
355-
void smallRegionRemoval(const Mat &harta, int t, Mat &out);
356359
Matching(int maxDisp, int scallingFactor = 4,int confidenceCheck = 6);
357360
Matching(void);
358361
~Matching(void);

0 commit comments

Comments
 (0)