Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Tetragramm
GitHub Repository: Tetragramm/opencv
Path: blob/master/modules/stitching/src/cuda/build_warp_maps.cu
16337 views
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
#if !defined CUDA_DISABLER
44
45
#include "opencv2/core/cuda/common.hpp"
46
#include "opencv2/core/cuda/vec_traits.hpp"
47
#include "opencv2/core/cuda/vec_math.hpp"
48
#include "opencv2/core/cuda/saturate_cast.hpp"
49
#include "opencv2/core/cuda/border_interpolate.hpp"
50
51
namespace cv { namespace cuda { namespace device
52
{
53
namespace imgproc
54
{
55
// TODO use intrinsics like __sinf and so on
56
57
namespace build_warp_maps
58
{
59
60
__constant__ float ck_rinv[9];
61
__constant__ float cr_kinv[9];
62
__constant__ float ct[3];
63
__constant__ float cscale;
64
}
65
66
67
class PlaneMapper
68
{
69
public:
70
static __device__ __forceinline__ void mapBackward(float u, float v, float &x, float &y)
71
{
72
using namespace build_warp_maps;
73
74
float x_ = u / cscale - ct[0];
75
float y_ = v / cscale - ct[1];
76
77
float z;
78
x = ck_rinv[0] * x_ + ck_rinv[1] * y_ + ck_rinv[2] * (1 - ct[2]);
79
y = ck_rinv[3] * x_ + ck_rinv[4] * y_ + ck_rinv[5] * (1 - ct[2]);
80
z = ck_rinv[6] * x_ + ck_rinv[7] * y_ + ck_rinv[8] * (1 - ct[2]);
81
82
x /= z;
83
y /= z;
84
}
85
};
86
87
88
class CylindricalMapper
89
{
90
public:
91
static __device__ __forceinline__ void mapBackward(float u, float v, float &x, float &y)
92
{
93
using namespace build_warp_maps;
94
95
u /= cscale;
96
float x_ = ::sinf(u);
97
float y_ = v / cscale;
98
float z_ = ::cosf(u);
99
100
float z;
101
x = ck_rinv[0] * x_ + ck_rinv[1] * y_ + ck_rinv[2] * z_;
102
y = ck_rinv[3] * x_ + ck_rinv[4] * y_ + ck_rinv[5] * z_;
103
z = ck_rinv[6] * x_ + ck_rinv[7] * y_ + ck_rinv[8] * z_;
104
105
if (z > 0) { x /= z; y /= z; }
106
else x = y = -1;
107
}
108
};
109
110
111
class SphericalMapper
112
{
113
public:
114
static __device__ __forceinline__ void mapBackward(float u, float v, float &x, float &y)
115
{
116
using namespace build_warp_maps;
117
118
v /= cscale;
119
u /= cscale;
120
121
float sinv = ::sinf(v);
122
float x_ = sinv * ::sinf(u);
123
float y_ = -::cosf(v);
124
float z_ = sinv * ::cosf(u);
125
126
float z;
127
x = ck_rinv[0] * x_ + ck_rinv[1] * y_ + ck_rinv[2] * z_;
128
y = ck_rinv[3] * x_ + ck_rinv[4] * y_ + ck_rinv[5] * z_;
129
z = ck_rinv[6] * x_ + ck_rinv[7] * y_ + ck_rinv[8] * z_;
130
131
if (z > 0) { x /= z; y /= z; }
132
else x = y = -1;
133
}
134
};
135
136
137
template <typename Mapper>
138
__global__ void buildWarpMapsKernel(int tl_u, int tl_v, int cols, int rows,
139
PtrStepf map_x, PtrStepf map_y)
140
{
141
int du = blockIdx.x * blockDim.x + threadIdx.x;
142
int dv = blockIdx.y * blockDim.y + threadIdx.y;
143
if (du < cols && dv < rows)
144
{
145
float u = tl_u + du;
146
float v = tl_v + dv;
147
float x, y;
148
Mapper::mapBackward(u, v, x, y);
149
map_x.ptr(dv)[du] = x;
150
map_y.ptr(dv)[du] = y;
151
}
152
}
153
154
155
void buildWarpPlaneMaps(int tl_u, int tl_v, PtrStepSzf map_x, PtrStepSzf map_y,
156
const float k_rinv[9], const float r_kinv[9], const float t[3],
157
float scale, cudaStream_t stream)
158
{
159
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::ck_rinv, k_rinv, 9*sizeof(float)));
160
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::cr_kinv, r_kinv, 9*sizeof(float)));
161
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::ct, t, 3*sizeof(float)));
162
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::cscale, &scale, sizeof(float)));
163
164
int cols = map_x.cols;
165
int rows = map_x.rows;
166
167
dim3 threads(32, 8);
168
dim3 grid(divUp(cols, threads.x), divUp(rows, threads.y));
169
170
buildWarpMapsKernel<PlaneMapper><<<grid,threads>>>(tl_u, tl_v, cols, rows, map_x, map_y);
171
cudaSafeCall(cudaGetLastError());
172
if (stream == 0)
173
cudaSafeCall(cudaDeviceSynchronize());
174
}
175
176
177
void buildWarpCylindricalMaps(int tl_u, int tl_v, PtrStepSzf map_x, PtrStepSzf map_y,
178
const float k_rinv[9], const float r_kinv[9], float scale,
179
cudaStream_t stream)
180
{
181
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::ck_rinv, k_rinv, 9*sizeof(float)));
182
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::cr_kinv, r_kinv, 9*sizeof(float)));
183
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::cscale, &scale, sizeof(float)));
184
185
int cols = map_x.cols;
186
int rows = map_x.rows;
187
188
dim3 threads(32, 8);
189
dim3 grid(divUp(cols, threads.x), divUp(rows, threads.y));
190
191
buildWarpMapsKernel<CylindricalMapper><<<grid,threads>>>(tl_u, tl_v, cols, rows, map_x, map_y);
192
cudaSafeCall(cudaGetLastError());
193
if (stream == 0)
194
cudaSafeCall(cudaDeviceSynchronize());
195
}
196
197
198
void buildWarpSphericalMaps(int tl_u, int tl_v, PtrStepSzf map_x, PtrStepSzf map_y,
199
const float k_rinv[9], const float r_kinv[9], float scale,
200
cudaStream_t stream)
201
{
202
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::ck_rinv, k_rinv, 9*sizeof(float)));
203
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::cr_kinv, r_kinv, 9*sizeof(float)));
204
cudaSafeCall(cudaMemcpyToSymbol(build_warp_maps::cscale, &scale, sizeof(float)));
205
206
int cols = map_x.cols;
207
int rows = map_x.rows;
208
209
dim3 threads(32, 8);
210
dim3 grid(divUp(cols, threads.x), divUp(rows, threads.y));
211
212
buildWarpMapsKernel<SphericalMapper><<<grid,threads>>>(tl_u, tl_v, cols, rows, map_x, map_y);
213
cudaSafeCall(cudaGetLastError());
214
if (stream == 0)
215
cudaSafeCall(cudaDeviceSynchronize());
216
}
217
} // namespace imgproc
218
}}} // namespace cv { namespace cuda { namespace cudev {
219
220
221
#endif /* CUDA_DISABLER */
222
223