disabled perf test on distance transform
[profile/ivi/opencv.git] / modules / stitching / include / opencv2 / stitching / detail / warpers.hpp
1  /*M///////////////////////////////////////////////////////////////////////////////////////
2 //
3 //  IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
4 //
5 //  By downloading, copying, installing or using the software you agree to this license.
6 //  If you do not agree to this license, do not download, install,
7 //  copy or use the software.
8 //
9 //
10 //                          License Agreement
11 //                For Open Source Computer Vision Library
12 //
13 // Copyright (C) 2000-2008, Intel Corporation, all rights reserved.
14 // Copyright (C) 2009, Willow Garage Inc., all rights reserved.
15 // Third party copyrights are property of their respective owners.
16 //
17 // Redistribution and use in source and binary forms, with or without modification,
18 // are permitted provided that the following conditions are met:
19 //
20 //   * Redistribution's of source code must retain the above copyright notice,
21 //     this list of conditions and the following disclaimer.
22 //
23 //   * Redistribution's in binary form must reproduce the above copyright notice,
24 //     this list of conditions and the following disclaimer in the documentation
25 //     and/or other materials provided with the distribution.
26 //
27 //   * The name of the copyright holders may not be used to endorse or promote products
28 //     derived from this software without specific prior written permission.
29 //
30 // This software is provided by the copyright holders and contributors "as is" and
31 // any express or implied warranties, including, but not limited to, the implied
32 // warranties of merchantability and fitness for a particular purpose are disclaimed.
33 // In no event shall the Intel Corporation or contributors be liable for any direct,
34 // indirect, incidental, special, exemplary, or consequential damages
35 // (including, but not limited to, procurement of substitute goods or services;
36 // loss of use, data, or profits; or business interruption) however caused
37 // and on any theory of liability, whether in contract, strict liability,
38 // or tort (including negligence or otherwise) arising in any way out of
39 // the use of this software, even if advised of the possibility of such damage.
40 //
41 //M*/
42
43 #ifndef __OPENCV_STITCHING_WARPERS_HPP__
44 #define __OPENCV_STITCHING_WARPERS_HPP__
45
46 #include "opencv2/core/core.hpp"
47 #include "opencv2/imgproc/imgproc.hpp"
48 #include "opencv2/opencv_modules.hpp"
49 #ifdef HAVE_OPENCV_GPU
50 # include "opencv2/gpu/gpu.hpp"
51 #endif
52
53 namespace cv {
54 namespace detail {
55
56 class CV_EXPORTS RotationWarper
57 {
58 public:
59     virtual ~RotationWarper() {}
60
61     virtual Point2f warpPoint(const Point2f &pt, const Mat &K, const Mat &R) = 0;
62
63     virtual Rect buildMaps(Size src_size, const Mat &K, const Mat &R, Mat &xmap, Mat &ymap) = 0;
64
65     virtual Point warp(const Mat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
66                        Mat &dst) = 0;
67
68     virtual void warpBackward(const Mat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
69                               Size dst_size, Mat &dst) = 0;
70
71     virtual Rect warpRoi(Size src_size, const Mat &K, const Mat &R) = 0;
72
73     virtual float getScale() const { return 1.f; }
74     virtual void setScale(float) {}
75 };
76
77
78 struct CV_EXPORTS ProjectorBase
79 {
80     void setCameraParams(const Mat &K = Mat::eye(3, 3, CV_32F),
81                          const Mat &R = Mat::eye(3, 3, CV_32F),
82                          const Mat &T = Mat::zeros(3, 1, CV_32F));
83
84     float scale;
85     float k[9];
86     float rinv[9];
87     float r_kinv[9];
88     float k_rinv[9];
89     float t[3];
90 };
91
92
93 template <class P>
94 class CV_EXPORTS RotationWarperBase : public RotationWarper
95 {
96 public:
97     Point2f warpPoint(const Point2f &pt, const Mat &K, const Mat &R);
98
99     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, Mat &xmap, Mat &ymap);
100
101     Point warp(const Mat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
102                Mat &dst);
103
104     void warpBackward(const Mat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
105                       Size dst_size, Mat &dst);
106
107     Rect warpRoi(Size src_size, const Mat &K, const Mat &R);
108
109     float getScale() const { return projector_.scale; }
110     void setScale(float val) { projector_.scale = val; }
111
112 protected:
113
114     // Detects ROI of the destination image. It's correct for any projection.
115     virtual void detectResultRoi(Size src_size, Point &dst_tl, Point &dst_br);
116
117     // Detects ROI of the destination image by walking over image border.
118     // Correctness for any projection isn't guaranteed.
119     void detectResultRoiByBorder(Size src_size, Point &dst_tl, Point &dst_br);
120
121     P projector_;
122 };
123
124
125 struct CV_EXPORTS PlaneProjector : ProjectorBase
126 {
127     void mapForward(float x, float y, float &u, float &v);
128     void mapBackward(float u, float v, float &x, float &y);
129 };
130
131
132 class CV_EXPORTS PlaneWarper : public RotationWarperBase<PlaneProjector>
133 {
134 public:
135     PlaneWarper(float scale = 1.f) { projector_.scale = scale; }
136
137     Point2f warpPoint(const Point2f &pt, const Mat &K, const Mat &R, const Mat &T);
138
139     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, const Mat &T, Mat &xmap, Mat &ymap);
140
141     Point warp(const Mat &src, const Mat &K, const Mat &R, const Mat &T, int interp_mode, int border_mode,
142                Mat &dst);
143
144     Rect warpRoi(Size src_size, const Mat &K, const Mat &R, const Mat &T);
145
146 protected:
147     void detectResultRoi(Size src_size, Point &dst_tl, Point &dst_br);
148 };
149
150
151 struct CV_EXPORTS SphericalProjector : ProjectorBase
152 {
153     void mapForward(float x, float y, float &u, float &v);
154     void mapBackward(float u, float v, float &x, float &y);
155 };
156
157
158 // Projects image onto unit sphere with origin at (0, 0, 0).
159 // Poles are located at (0, -1, 0) and (0, 1, 0) points.
160 class CV_EXPORTS SphericalWarper : public RotationWarperBase<SphericalProjector>
161 {
162 public:
163     SphericalWarper(float scale) { projector_.scale = scale; }
164
165 protected:
166     void detectResultRoi(Size src_size, Point &dst_tl, Point &dst_br);
167 };
168
169
170 struct CV_EXPORTS CylindricalProjector : ProjectorBase
171 {
172     void mapForward(float x, float y, float &u, float &v);
173     void mapBackward(float u, float v, float &x, float &y);
174 };
175
176
177 // Projects image onto x * x + z * z = 1 cylinder
178 class CV_EXPORTS CylindricalWarper : public RotationWarperBase<CylindricalProjector>
179 {
180 public:
181     CylindricalWarper(float scale) { projector_.scale = scale; }
182
183 protected:
184     void detectResultRoi(Size src_size, Point &dst_tl, Point &dst_br)
185     {
186         RotationWarperBase<CylindricalProjector>::detectResultRoiByBorder(src_size, dst_tl, dst_br);
187     }
188 };
189
190
191 struct CV_EXPORTS FisheyeProjector : ProjectorBase
192 {
193     void mapForward(float x, float y, float &u, float &v);
194     void mapBackward(float u, float v, float &x, float &y);
195 };
196
197
198 class CV_EXPORTS FisheyeWarper : public RotationWarperBase<FisheyeProjector>
199 {
200 public:
201     FisheyeWarper(float scale) { projector_.scale = scale; }
202 };
203
204
205 struct CV_EXPORTS StereographicProjector : ProjectorBase
206 {
207     void mapForward(float x, float y, float &u, float &v);
208     void mapBackward(float u, float v, float &x, float &y);
209 };
210
211
212 class CV_EXPORTS StereographicWarper : public RotationWarperBase<StereographicProjector>
213 {
214 public:
215     StereographicWarper(float scale) { projector_.scale = scale; }
216 };
217
218
219 struct CV_EXPORTS CompressedRectilinearProjector : ProjectorBase
220 {
221         float a, b;
222
223     void mapForward(float x, float y, float &u, float &v);
224     void mapBackward(float u, float v, float &x, float &y);
225 };
226
227
228 class CV_EXPORTS CompressedRectilinearWarper : public RotationWarperBase<CompressedRectilinearProjector>
229 {
230 public:
231     CompressedRectilinearWarper(float scale, float A = 1, float B = 1)
232     {
233         projector_.a = A;
234         projector_.b = B;
235         projector_.scale = scale;
236     }
237 };
238
239
240 struct CV_EXPORTS CompressedRectilinearPortraitProjector : ProjectorBase
241 {
242         float a, b;
243
244     void mapForward(float x, float y, float &u, float &v);
245     void mapBackward(float u, float v, float &x, float &y);
246 };
247
248
249 class CV_EXPORTS CompressedRectilinearPortraitWarper : public RotationWarperBase<CompressedRectilinearPortraitProjector>
250 {
251 public:
252    CompressedRectilinearPortraitWarper(float scale, float A = 1, float B = 1)
253    {
254            projector_.a = A;
255            projector_.b = B;
256        projector_.scale = scale;
257    }
258 };
259
260
261 struct CV_EXPORTS PaniniProjector : ProjectorBase
262 {
263         float a, b;
264
265     void mapForward(float x, float y, float &u, float &v);
266     void mapBackward(float u, float v, float &x, float &y);
267 };
268
269
270 class CV_EXPORTS PaniniWarper : public RotationWarperBase<PaniniProjector>
271 {
272 public:
273    PaniniWarper(float scale, float A = 1, float B = 1)
274    {
275            projector_.a = A;
276            projector_.b = B;
277        projector_.scale = scale;
278    }
279 };
280
281
282 struct CV_EXPORTS PaniniPortraitProjector : ProjectorBase
283 {
284         float a, b;
285
286     void mapForward(float x, float y, float &u, float &v);
287     void mapBackward(float u, float v, float &x, float &y);
288 };
289
290
291 class CV_EXPORTS PaniniPortraitWarper : public RotationWarperBase<PaniniPortraitProjector>
292 {
293 public:
294    PaniniPortraitWarper(float scale, float A = 1, float B = 1)
295    {
296            projector_.a = A;
297            projector_.b = B;
298        projector_.scale = scale;
299    }
300
301 };
302
303
304 struct CV_EXPORTS MercatorProjector : ProjectorBase
305 {
306     void mapForward(float x, float y, float &u, float &v);
307     void mapBackward(float u, float v, float &x, float &y);
308 };
309
310
311 class CV_EXPORTS MercatorWarper : public RotationWarperBase<MercatorProjector>
312 {
313 public:
314     MercatorWarper(float scale) { projector_.scale = scale; }
315 };
316
317
318 struct CV_EXPORTS TransverseMercatorProjector : ProjectorBase
319 {
320     void mapForward(float x, float y, float &u, float &v);
321     void mapBackward(float u, float v, float &x, float &y);
322 };
323
324
325 class CV_EXPORTS TransverseMercatorWarper : public RotationWarperBase<TransverseMercatorProjector>
326 {
327 public:
328     TransverseMercatorWarper(float scale) { projector_.scale = scale; }
329 };
330
331
332 #ifdef HAVE_OPENCV_GPU
333 class CV_EXPORTS PlaneWarperGpu : public PlaneWarper
334 {
335 public:
336     PlaneWarperGpu(float scale = 1.f) : PlaneWarper(scale) {}
337
338     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, Mat &xmap, Mat &ymap)
339     {
340         Rect result = buildMaps(src_size, K, R, d_xmap_, d_ymap_);
341         d_xmap_.download(xmap);
342         d_ymap_.download(ymap);
343         return result;
344     }
345
346     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, const Mat &T, Mat &xmap, Mat &ymap)
347     {
348         Rect result = buildMaps(src_size, K, R, T, d_xmap_, d_ymap_);
349         d_xmap_.download(xmap);
350         d_ymap_.download(ymap);
351         return result;
352     }
353
354     Point warp(const Mat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
355                Mat &dst)
356     {
357         d_src_.upload(src);
358         Point result = warp(d_src_, K, R, interp_mode, border_mode, d_dst_);
359         d_dst_.download(dst);
360         return result;
361     }
362
363     Point warp(const Mat &src, const Mat &K, const Mat &R, const Mat &T, int interp_mode, int border_mode,
364                Mat &dst)
365     {
366         d_src_.upload(src);
367         Point result = warp(d_src_, K, R, T, interp_mode, border_mode, d_dst_);
368         d_dst_.download(dst);
369         return result;
370     }
371
372     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, gpu::GpuMat &xmap, gpu::GpuMat &ymap);
373
374     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, const Mat &T, gpu::GpuMat &xmap, gpu::GpuMat &ymap);
375
376     Point warp(const gpu::GpuMat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
377                gpu::GpuMat &dst);
378
379     Point warp(const gpu::GpuMat &src, const Mat &K, const Mat &R, const Mat &T, int interp_mode, int border_mode,
380                gpu::GpuMat &dst);
381
382 private:
383     gpu::GpuMat d_xmap_, d_ymap_, d_src_, d_dst_;
384 };
385
386
387 class CV_EXPORTS SphericalWarperGpu : public SphericalWarper
388 {
389 public:
390     SphericalWarperGpu(float scale) : SphericalWarper(scale) {}
391
392     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, Mat &xmap, Mat &ymap)
393     {
394         Rect result = buildMaps(src_size, K, R, d_xmap_, d_ymap_);
395         d_xmap_.download(xmap);
396         d_ymap_.download(ymap);
397         return result;
398     }
399
400     Point warp(const Mat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
401                Mat &dst)
402     {
403         d_src_.upload(src);
404         Point result = warp(d_src_, K, R, interp_mode, border_mode, d_dst_);
405         d_dst_.download(dst);
406         return result;
407     }
408
409     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, gpu::GpuMat &xmap, gpu::GpuMat &ymap);
410
411     Point warp(const gpu::GpuMat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
412                gpu::GpuMat &dst);
413
414 private:
415     gpu::GpuMat d_xmap_, d_ymap_, d_src_, d_dst_;
416 };
417
418
419 class CV_EXPORTS CylindricalWarperGpu : public CylindricalWarper
420 {
421 public:
422     CylindricalWarperGpu(float scale) : CylindricalWarper(scale) {}
423
424     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, Mat &xmap, Mat &ymap)
425     {
426         Rect result = buildMaps(src_size, K, R, d_xmap_, d_ymap_);
427         d_xmap_.download(xmap);
428         d_ymap_.download(ymap);
429         return result;
430     }
431
432     Point warp(const Mat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
433                Mat &dst)
434     {
435         d_src_.upload(src);
436         Point result = warp(d_src_, K, R, interp_mode, border_mode, d_dst_);
437         d_dst_.download(dst);
438         return result;
439     }
440
441     Rect buildMaps(Size src_size, const Mat &K, const Mat &R, gpu::GpuMat &xmap, gpu::GpuMat &ymap);
442
443     Point warp(const gpu::GpuMat &src, const Mat &K, const Mat &R, int interp_mode, int border_mode,
444                gpu::GpuMat &dst);
445
446 private:
447     gpu::GpuMat d_xmap_, d_ymap_, d_src_, d_dst_;
448 };
449 #endif
450
451
452 struct SphericalPortraitProjector : ProjectorBase
453 {
454     void mapForward(float x, float y, float &u, float &v);
455     void mapBackward(float u, float v, float &x, float &y);
456 };
457
458
459 // Projects image onto unit sphere with origin at (0, 0, 0).
460 // Poles are located NOT at (0, -1, 0) and (0, 1, 0) points, BUT at (1, 0, 0) and (-1, 0, 0) points.
461 class SphericalPortraitWarper : public RotationWarperBase<SphericalPortraitProjector>
462 {
463 public:
464     SphericalPortraitWarper(float scale) { projector_.scale = scale; }
465
466 protected:
467     void detectResultRoi(Size src_size, Point &dst_tl, Point &dst_br);
468 };
469
470 struct CylindricalPortraitProjector : ProjectorBase
471 {
472     void mapForward(float x, float y, float &u, float &v);
473     void mapBackward(float u, float v, float &x, float &y);
474 };
475
476
477 class CylindricalPortraitWarper : public RotationWarperBase<CylindricalPortraitProjector>
478 {
479 public:
480     CylindricalPortraitWarper(float scale) { projector_.scale = scale; }
481
482 protected:
483     void detectResultRoi(Size src_size, Point &dst_tl, Point &dst_br)
484     {
485         RotationWarperBase<CylindricalPortraitProjector>::detectResultRoiByBorder(src_size, dst_tl, dst_br);
486     }
487 };
488
489 struct PlanePortraitProjector : ProjectorBase
490 {
491     void mapForward(float x, float y, float &u, float &v);
492     void mapBackward(float u, float v, float &x, float &y);
493 };
494
495
496 class PlanePortraitWarper : public RotationWarperBase<PlanePortraitProjector>
497 {
498 public:
499     PlanePortraitWarper(float scale) { projector_.scale = scale; }
500
501 protected:
502     void detectResultRoi(Size src_size, Point &dst_tl, Point &dst_br)
503     {
504         RotationWarperBase<PlanePortraitProjector>::detectResultRoiByBorder(src_size, dst_tl, dst_br);
505     }
506 };
507
508 } // namespace detail
509 } // namespace cv
510
511 #include "warpers_inl.hpp"
512
513 #endif // __OPENCV_STITCHING_WARPERS_HPP__