@@ -23,13 +23,13 @@ const String keys =
23
23
" {algorithm |bm | stereo matching method (bm or sgbm) }"
24
24
" {filter |wls_conf | used post-filtering (wls_conf or wls_no_conf) }"
25
25
" {no-display | | don't display results }"
26
- " {no-downscale | | prevent stereo matching on downscaled views }"
26
+ " {no-downscale | | force stereo matching on full-sized views to improve quality }"
27
27
" {dst_conf_path |None | optional path to save the confidence map used in filtering }"
28
28
" {vis_mult |1.0 | coefficient used to scale disparity map visualizations }"
29
29
" {max_disparity |160 | parameter of stereo matching }"
30
- " {window_size |19 | parameter of stereo matching }"
30
+ " {window_size |-1 | parameter of stereo matching }"
31
31
" {wls_lambda |8000.0 | parameter of post-filtering }"
32
- " {wls_sigma |1.0 | parameter of post-filtering }"
32
+ " {wls_sigma |1.5 | parameter of post-filtering }"
33
33
;
34
34
35
35
int main (int argc, char ** argv)
@@ -54,17 +54,30 @@ int main(int argc, char** argv)
54
54
bool no_display = parser.has (" no-display" );
55
55
bool no_downscale = parser.has (" no-downscale" );
56
56
int max_disp = parser.get <int >(" max_disparity" );
57
- int wsize = parser.get <int >(" window_size" );
58
57
double lambda = parser.get <double >(" wls_lambda" );
59
58
double sigma = parser.get <double >(" wls_sigma" );
60
59
double vis_mult = parser.get <double >(" vis_mult" );
61
60
61
+ int wsize;
62
+ if (parser.get <int >(" window_size" )>=0 ) // user provided window_size value
63
+ wsize = parser.get <int >(" window_size" );
64
+ else
65
+ {
66
+ if (algo==" sgbm" )
67
+ wsize = 3 ; // default window size for SGBM
68
+ else if (!no_downscale && algo==" bm" && filter==" wls_conf" )
69
+ wsize = 7 ; // default window size for BM on downscaled views (downscaling is performed only for wls_conf)
70
+ else
71
+ wsize = 15 ; // default window size for BM on full-sized views
72
+ }
73
+
62
74
if (!parser.check ())
63
75
{
64
76
parser.printErrors ();
65
77
return -1 ;
66
78
}
67
79
80
+ // ! [load_views]
68
81
Mat left = imread (left_im ,IMREAD_COLOR);
69
82
if ( left.empty () )
70
83
{
@@ -78,6 +91,7 @@ int main(int argc, char** argv)
78
91
cout<<" Cannot read image file: " <<right_im;
79
92
return -1 ;
80
93
}
94
+ // ! [load_views]
81
95
82
96
bool noGT;
83
97
Mat GT_disp;
@@ -99,6 +113,7 @@ int main(int argc, char** argv)
99
113
Mat conf_map = Mat (left.rows ,left.cols ,CV_8U);
100
114
conf_map = Scalar (255 );
101
115
Rect ROI;
116
+ Ptr<DisparityWLSFilter> wls_filter;
102
117
double matching_time, filtering_time;
103
118
if (max_disp<=0 || max_disp%16 !=0 )
104
119
{
@@ -110,56 +125,51 @@ int main(int argc, char** argv)
110
125
cout<<" Incorrect window_size value: it should be positive and odd" ;
111
126
return -1 ;
112
127
}
113
- if (filter==" wls_conf" )
128
+ if (filter==" wls_conf" ) // filtering with confidence (significantly better quality than wls_no_conf)
114
129
{
115
130
if (!no_downscale)
116
131
{
117
- wsize = wsize/2 ;
118
- if (wsize%2 ==0 ) wsize++;
132
+ // downscale the views to speed-up the matching stage, as we will need to compute both left
133
+ // and right disparity maps for confidence map computation
134
+ // ! [downscale]
119
135
max_disp/=2 ;
120
136
if (max_disp%16 !=0 )
121
137
max_disp += 16 -(max_disp%16 );
122
138
resize (left ,left_for_matcher ,Size (),0.5 ,0.5 );
123
139
resize (right,right_for_matcher,Size (),0.5 ,0.5 );
140
+ // ! [downscale]
124
141
}
125
142
else
126
143
{
127
144
left_for_matcher = left.clone ();
128
145
right_for_matcher = right.clone ();
129
146
}
130
147
131
-
132
148
if (algo==" bm" )
133
149
{
134
- Ptr<StereoBM> left_matcher = StereoBM::create (max_disp,wsize);
135
- left_matcher->setMinDisparity (0 );
136
- Ptr<StereoBM> right_matcher = StereoBM::create (max_disp,wsize);
137
- right_matcher->setMinDisparity (-max_disp+1 );
138
- left_matcher->setTextureThreshold (0 );
139
- left_matcher->setUniquenessRatio (0 );
140
- right_matcher->setTextureThreshold (0 );
141
- right_matcher->setUniquenessRatio (0 );
142
- cvtColor (left_for_matcher, left_for_matcher, COLOR_BGR2GRAY);
150
+ // ! [matching]
151
+ Ptr<StereoBM> left_matcher = StereoBM::create (max_disp,wsize);
152
+ wls_filter = createDisparityWLSFilter (left_matcher);
153
+ Ptr<StereoMatcher> right_matcher = createRightMatcher (left_matcher);
154
+
155
+ cvtColor (left_for_matcher, left_for_matcher, COLOR_BGR2GRAY);
143
156
cvtColor (right_for_matcher, right_for_matcher, COLOR_BGR2GRAY);
144
- ROI = computeROI (left_for_matcher.size (),left_matcher);
145
157
146
158
matching_time = (double )getTickCount ();
147
159
left_matcher-> compute (left_for_matcher, right_for_matcher,left_disp);
148
160
right_matcher->compute (right_for_matcher,left_for_matcher, right_disp);
149
161
matching_time = ((double )getTickCount () - matching_time)/getTickFrequency ();
162
+ // ! [matching]
150
163
}
151
164
else if (algo==" sgbm" )
152
165
{
153
166
Ptr<StereoSGBM> left_matcher = StereoSGBM::create (0 ,max_disp,wsize);
154
- left_matcher->setMinDisparity (0 );
155
- Ptr<StereoSGBM> right_matcher = StereoSGBM::create (-max_disp+1 ,max_disp,wsize);
156
- left_matcher->setUniquenessRatio (0 );
157
- left_matcher->setDisp12MaxDiff (1000000 );
158
- left_matcher->setSpeckleWindowSize (0 );
159
- right_matcher->setUniquenessRatio (0 );
160
- right_matcher->setDisp12MaxDiff (1000000 );
161
- right_matcher->setSpeckleWindowSize (0 );
162
- ROI = computeROI (left_for_matcher.size (),left_matcher);
167
+ left_matcher->setP1 (24 *wsize*wsize);
168
+ left_matcher->setP2 (96 *wsize*wsize);
169
+ left_matcher->setPreFilterCap (63 );
170
+ left_matcher->setMode (StereoSGBM::MODE_SGBM_3WAY);
171
+ wls_filter = createDisparityWLSFilter (left_matcher);
172
+ Ptr<StereoMatcher> right_matcher = createRightMatcher (left_matcher);
163
173
164
174
matching_time = (double )getTickCount ();
165
175
left_matcher-> compute (left_for_matcher, right_for_matcher,left_disp);
@@ -172,14 +182,17 @@ int main(int argc, char** argv)
172
182
return -1 ;
173
183
}
174
184
175
- Ptr<DisparityWLSFilter> wls_filter = createDisparityWLSFilter ( true );
185
+ // ! [filtering]
176
186
wls_filter->setLambda (lambda);
177
187
wls_filter->setSigmaColor (sigma);
178
188
filtering_time = (double )getTickCount ();
179
- wls_filter->filter (left_disp,left,filtered_disp,ROI, right_disp);
189
+ wls_filter->filter (left_disp,left,filtered_disp,right_disp);
180
190
filtering_time = ((double )getTickCount () - filtering_time)/getTickFrequency ();
191
+ // ! [filtering]
181
192
conf_map = wls_filter->getConfidenceMap ();
182
193
194
+ // Get the ROI that was used in the last filter call:
195
+ ROI = wls_filter->getROI ();
183
196
if (!no_downscale)
184
197
{
185
198
// upscale raw disparity and ROI back for a proper comparison:
@@ -190,6 +203,9 @@ int main(int argc, char** argv)
190
203
}
191
204
else if (filter==" wls_no_conf" )
192
205
{
206
+ /* There is no convenience function for the case of filtering with no confidence, so we
207
+ will need to set the ROI and matcher parameters manually */
208
+
193
209
left_for_matcher = left.clone ();
194
210
right_for_matcher = right.clone ();
195
211
@@ -201,6 +217,8 @@ int main(int argc, char** argv)
201
217
cvtColor (left_for_matcher, left_for_matcher, COLOR_BGR2GRAY);
202
218
cvtColor (right_for_matcher, right_for_matcher, COLOR_BGR2GRAY);
203
219
ROI = computeROI (left_for_matcher.size (),matcher);
220
+ wls_filter = createDisparityWLSFilterGeneric (false );
221
+ wls_filter->setDepthDiscontinuityRadius ((int )ceil (0.33 *wsize));
204
222
205
223
matching_time = (double )getTickCount ();
206
224
matcher->compute (left_for_matcher,right_for_matcher,left_disp);
@@ -212,7 +230,12 @@ int main(int argc, char** argv)
212
230
matcher->setUniquenessRatio (0 );
213
231
matcher->setDisp12MaxDiff (1000000 );
214
232
matcher->setSpeckleWindowSize (0 );
233
+ matcher->setP1 (24 *wsize*wsize);
234
+ matcher->setP2 (96 *wsize*wsize);
235
+ matcher->setMode (StereoSGBM::MODE_SGBM_3WAY);
215
236
ROI = computeROI (left_for_matcher.size (),matcher);
237
+ wls_filter = createDisparityWLSFilterGeneric (false );
238
+ wls_filter->setDepthDiscontinuityRadius ((int )ceil (0.5 *wsize));
216
239
217
240
matching_time = (double )getTickCount ();
218
241
matcher->compute (left_for_matcher,right_for_matcher,left_disp);
@@ -224,11 +247,10 @@ int main(int argc, char** argv)
224
247
return -1 ;
225
248
}
226
249
227
- Ptr<DisparityWLSFilter> wls_filter = createDisparityWLSFilter (false );
228
250
wls_filter->setLambda (lambda);
229
251
wls_filter->setSigmaColor (sigma);
230
252
filtering_time = (double )getTickCount ();
231
- wls_filter->filter (left_disp,left,filtered_disp,ROI);
253
+ wls_filter->filter (left_disp,left,filtered_disp,Mat (), ROI);
232
254
filtering_time = ((double )getTickCount () - filtering_time)/getTickFrequency ();
233
255
}
234
256
else
@@ -292,6 +314,7 @@ int main(int argc, char** argv)
292
314
imshow (" ground-truth disparity" , GT_disp_vis);
293
315
}
294
316
317
+ // ! [visualization]
295
318
Mat raw_disp_vis;
296
319
getDisparityVis (left_disp,raw_disp_vis,vis_mult);
297
320
namedWindow (" raw disparity" , WINDOW_AUTOSIZE);
@@ -301,6 +324,7 @@ int main(int argc, char** argv)
301
324
namedWindow (" filtered disparity" , WINDOW_AUTOSIZE);
302
325
imshow (" filtered disparity" , filtered_disp_vis);
303
326
waitKey ();
327
+ // ! [visualization]
304
328
}
305
329
306
330
return 0 ;
0 commit comments