41 #ifndef PCL_INTEGRAL_IMAGE2D_IMPL_H_
42 #define PCL_INTEGRAL_IMAGE2D_IMPL_H_
50 template <
typename DataType,
unsigned Dimension>
void
53 compute_second_order_integral_images_ = compute_second_order_integral_images;
57 template <
typename DataType,
unsigned Dimension>
void
60 if ((width + 1) * (height + 1) > first_order_integral_image_.size () )
64 first_order_integral_image_.resize ( (width_ + 1) * (height_ + 1) );
65 finite_values_integral_image_.resize ( (width_ + 1) * (height_ + 1) );
66 if (compute_second_order_integral_images_)
67 second_order_integral_image_.resize ( (width_ + 1) * (height_ + 1) );
69 computeIntegralImages (data, row_stride, element_stride);
75 unsigned start_x,
unsigned start_y,
unsigned width,
unsigned height)
const
77 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
78 const unsigned upper_right_idx = upper_left_idx + width;
79 const unsigned lower_left_idx = (start_y + height) * (width_ + 1) + start_x;
80 const unsigned lower_right_idx = lower_left_idx + width;
82 return (first_order_integral_image_[lower_right_idx] + first_order_integral_image_[upper_left_idx] -
83 first_order_integral_image_[upper_right_idx] - first_order_integral_image_[lower_left_idx] );
89 unsigned start_x,
unsigned start_y,
unsigned width,
unsigned height)
const
91 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
92 const unsigned upper_right_idx = upper_left_idx + width;
93 const unsigned lower_left_idx = (start_y + height) * (width_ + 1) + start_x;
94 const unsigned lower_right_idx = lower_left_idx + width;
96 return (second_order_integral_image_[lower_right_idx] + second_order_integral_image_[upper_left_idx] -
97 second_order_integral_image_[upper_right_idx] - second_order_integral_image_[lower_left_idx] );
101 template <
typename DataType,
unsigned Dimension>
unsigned
103 unsigned start_x,
unsigned start_y,
unsigned width,
unsigned height)
const
105 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
106 const unsigned upper_right_idx = upper_left_idx + width;
107 const unsigned lower_left_idx = (start_y + height) * (width_ + 1) + start_x;
108 const unsigned lower_right_idx = lower_left_idx + width;
110 return (finite_values_integral_image_[lower_right_idx] + finite_values_integral_image_[upper_left_idx] -
111 finite_values_integral_image_[upper_right_idx] - finite_values_integral_image_[lower_left_idx] );
117 unsigned start_x,
unsigned start_y,
unsigned end_x,
unsigned end_y)
const
119 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
120 const unsigned upper_right_idx = start_y * (width_ + 1) + end_x;
121 const unsigned lower_left_idx = end_y * (width_ + 1) + start_x;
122 const unsigned lower_right_idx = end_y * (width_ + 1) + end_x;
124 return (first_order_integral_image_[lower_right_idx] + first_order_integral_image_[upper_left_idx] -
125 first_order_integral_image_[upper_right_idx] - first_order_integral_image_[lower_left_idx] );
131 unsigned start_x,
unsigned start_y,
unsigned end_x,
unsigned end_y)
const
133 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
134 const unsigned upper_right_idx = start_y * (width_ + 1) + end_x;
135 const unsigned lower_left_idx = end_y * (width_ + 1) + start_x;
136 const unsigned lower_right_idx = end_y * (width_ + 1) + end_x;
138 return (second_order_integral_image_[lower_right_idx] + second_order_integral_image_[upper_left_idx] -
139 second_order_integral_image_[upper_right_idx] - second_order_integral_image_[lower_left_idx] );
143 template <
typename DataType,
unsigned Dimension>
unsigned
145 unsigned start_x,
unsigned start_y,
unsigned end_x,
unsigned end_y)
const
147 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
148 const unsigned upper_right_idx = start_y * (width_ + 1) + end_x;
149 const unsigned lower_left_idx = end_y * (width_ + 1) + start_x;
150 const unsigned lower_right_idx = end_y * (width_ + 1) + end_x;
152 return (finite_values_integral_image_[lower_right_idx] + finite_values_integral_image_[upper_left_idx] -
153 finite_values_integral_image_[upper_right_idx] - finite_values_integral_image_[lower_left_idx] );
157 template <
typename DataType,
unsigned Dimension>
void
159 const DataType *data,
unsigned row_stride,
unsigned element_stride)
161 ElementType* previous_row = &first_order_integral_image_[0];
162 ElementType* current_row = previous_row + (width_ + 1);
163 memset (previous_row, 0,
sizeof (
ElementType) * (width_ + 1));
165 unsigned* count_previous_row = &finite_values_integral_image_[0];
166 unsigned* count_current_row = count_previous_row + (width_ + 1);
167 memset (count_previous_row, 0,
sizeof (
unsigned) * (width_ + 1));
169 if (!compute_second_order_integral_images_)
171 for (
unsigned rowIdx = 0; rowIdx < height_; ++rowIdx, data += row_stride,
172 previous_row = current_row, current_row += (width_ + 1),
173 count_previous_row = count_current_row, count_current_row += (width_ + 1))
175 current_row [0].setZero ();
176 count_current_row [0] = 0;
177 for (
unsigned colIdx = 0, valIdx = 0; colIdx < width_; ++colIdx, valIdx += element_stride)
179 current_row [colIdx + 1] = previous_row [colIdx + 1] + current_row [colIdx] - previous_row [colIdx];
180 count_current_row [colIdx + 1] = count_previous_row [colIdx + 1] + count_current_row [colIdx] - count_previous_row [colIdx];
181 const InputType* element =
reinterpret_cast <const InputType*
> (&data [valIdx]);
182 if (std::isfinite (element->sum ()))
184 current_row [colIdx + 1] += element->template cast<typename IntegralImageTypeTraits<DataType>::IntegralType>();
185 ++(count_current_row [colIdx + 1]);
192 SecondOrderType* so_previous_row = &second_order_integral_image_[0];
193 SecondOrderType* so_current_row = so_previous_row + (width_ + 1);
197 for (
unsigned rowIdx = 0; rowIdx < height_; ++rowIdx, data += row_stride,
198 previous_row = current_row, current_row += (width_ + 1),
199 count_previous_row = count_current_row, count_current_row += (width_ + 1),
200 so_previous_row = so_current_row, so_current_row += (width_ + 1))
202 current_row [0].setZero ();
203 so_current_row [0].setZero ();
204 count_current_row [0] = 0;
205 for (
unsigned colIdx = 0, valIdx = 0; colIdx < width_; ++colIdx, valIdx += element_stride)
207 current_row [colIdx + 1] = previous_row [colIdx + 1] + current_row [colIdx] - previous_row [colIdx];
208 so_current_row [colIdx + 1] = so_previous_row [colIdx + 1] + so_current_row [colIdx] - so_previous_row [colIdx];
209 count_current_row [colIdx + 1] = count_previous_row [colIdx + 1] + count_current_row [colIdx] - count_previous_row [colIdx];
211 const InputType* element =
reinterpret_cast <const InputType*
> (&data [valIdx]);
212 if (std::isfinite (element->sum ()))
214 current_row [colIdx + 1] += element->template cast<typename IntegralImageTypeTraits<DataType>::IntegralType>();
215 ++(count_current_row [colIdx + 1]);
216 for (
unsigned myIdx = 0, elIdx = 0; myIdx < Dimension; ++myIdx)
217 for (
unsigned mxIdx = myIdx; mxIdx < Dimension; ++mxIdx, ++elIdx)
218 so_current_row [colIdx + 1][elIdx] += (*element)[myIdx] * (*element)[mxIdx];
226 template <
typename DataType>
void
229 if ((width + 1) * (height + 1) > first_order_integral_image_.size () )
233 first_order_integral_image_.resize ( (width_ + 1) * (height_ + 1) );
234 finite_values_integral_image_.resize ( (width_ + 1) * (height_ + 1) );
235 if (compute_second_order_integral_images_)
236 second_order_integral_image_.resize ( (width_ + 1) * (height_ + 1) );
238 computeIntegralImages (data, row_stride, element_stride);
244 unsigned start_x,
unsigned start_y,
unsigned width,
unsigned height)
const
246 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
247 const unsigned upper_right_idx = upper_left_idx + width;
248 const unsigned lower_left_idx = (start_y + height) * (width_ + 1) + start_x;
249 const unsigned lower_right_idx = lower_left_idx + width;
251 return (first_order_integral_image_[lower_right_idx] + first_order_integral_image_[upper_left_idx] -
252 first_order_integral_image_[upper_right_idx] - first_order_integral_image_[lower_left_idx] );
258 unsigned start_x,
unsigned start_y,
unsigned width,
unsigned height)
const
260 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
261 const unsigned upper_right_idx = upper_left_idx + width;
262 const unsigned lower_left_idx = (start_y + height) * (width_ + 1) + start_x;
263 const unsigned lower_right_idx = lower_left_idx + width;
265 return (second_order_integral_image_[lower_right_idx] + second_order_integral_image_[upper_left_idx] -
266 second_order_integral_image_[upper_right_idx] - second_order_integral_image_[lower_left_idx] );
270 template <
typename DataType>
unsigned
272 unsigned start_x,
unsigned start_y,
unsigned width,
unsigned height)
const
274 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
275 const unsigned upper_right_idx = upper_left_idx + width;
276 const unsigned lower_left_idx = (start_y + height) * (width_ + 1) + start_x;
277 const unsigned lower_right_idx = lower_left_idx + width;
279 return (finite_values_integral_image_[lower_right_idx] + finite_values_integral_image_[upper_left_idx] -
280 finite_values_integral_image_[upper_right_idx] - finite_values_integral_image_[lower_left_idx] );
286 unsigned start_x,
unsigned start_y,
unsigned end_x,
unsigned end_y)
const
288 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
289 const unsigned upper_right_idx = start_y * (width_ + 1) + end_x;
290 const unsigned lower_left_idx = end_y * (width_ + 1) + start_x;
291 const unsigned lower_right_idx = end_y * (width_ + 1) + end_x;
293 return (first_order_integral_image_[lower_right_idx] + first_order_integral_image_[upper_left_idx] -
294 first_order_integral_image_[upper_right_idx] - first_order_integral_image_[lower_left_idx] );
300 unsigned start_x,
unsigned start_y,
unsigned end_x,
unsigned end_y)
const
302 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
303 const unsigned upper_right_idx = start_y * (width_ + 1) + end_x;
304 const unsigned lower_left_idx = end_y * (width_ + 1) + start_x;
305 const unsigned lower_right_idx = end_y * (width_ + 1) + end_x;
307 return (second_order_integral_image_[lower_right_idx] + second_order_integral_image_[upper_left_idx] -
308 second_order_integral_image_[upper_right_idx] - second_order_integral_image_[lower_left_idx] );
312 template <
typename DataType>
unsigned
314 unsigned start_x,
unsigned start_y,
unsigned end_x,
unsigned end_y)
const
316 const unsigned upper_left_idx = start_y * (width_ + 1) + start_x;
317 const unsigned upper_right_idx = start_y * (width_ + 1) + end_x;
318 const unsigned lower_left_idx = end_y * (width_ + 1) + start_x;
319 const unsigned lower_right_idx = end_y * (width_ + 1) + end_x;
321 return (finite_values_integral_image_[lower_right_idx] + finite_values_integral_image_[upper_left_idx] -
322 finite_values_integral_image_[upper_right_idx] - finite_values_integral_image_[lower_left_idx] );
326 template <
typename DataType>
void
328 const DataType *data,
unsigned row_stride,
unsigned element_stride)
330 ElementType* previous_row = &first_order_integral_image_[0];
331 ElementType* current_row = previous_row + (width_ + 1);
332 memset (previous_row, 0,
sizeof (
ElementType) * (width_ + 1));
334 unsigned* count_previous_row = &finite_values_integral_image_[0];
335 unsigned* count_current_row = count_previous_row + (width_ + 1);
336 memset (count_previous_row, 0,
sizeof (
unsigned) * (width_ + 1));
338 if (!compute_second_order_integral_images_)
340 for (
unsigned rowIdx = 0; rowIdx < height_; ++rowIdx, data += row_stride,
341 previous_row = current_row, current_row += (width_ + 1),
342 count_previous_row = count_current_row, count_current_row += (width_ + 1))
344 current_row [0] = 0.0;
345 count_current_row [0] = 0;
346 for (
unsigned colIdx = 0, valIdx = 0; colIdx < width_; ++colIdx, valIdx += element_stride)
348 current_row [colIdx + 1] = previous_row [colIdx + 1] + current_row [colIdx] - previous_row [colIdx];
349 count_current_row [colIdx + 1] = count_previous_row [colIdx + 1] + count_current_row [colIdx] - count_previous_row [colIdx];
350 if (std::isfinite (data [valIdx]))
352 current_row [colIdx + 1] += data [valIdx];
353 ++(count_current_row [colIdx + 1]);
364 for (
unsigned rowIdx = 0; rowIdx < height_; ++rowIdx, data += row_stride,
365 previous_row = current_row, current_row += (width_ + 1),
366 count_previous_row = count_current_row, count_current_row += (width_ + 1),
367 so_previous_row = so_current_row, so_current_row += (width_ + 1))
369 current_row [0] = 0.0;
370 so_current_row [0] = 0.0;
371 count_current_row [0] = 0;
372 for (
unsigned colIdx = 0, valIdx = 0; colIdx < width_; ++colIdx, valIdx += element_stride)
374 current_row [colIdx + 1] = previous_row [colIdx + 1] + current_row [colIdx] - previous_row [colIdx];
375 so_current_row [colIdx + 1] = so_previous_row [colIdx + 1] + so_current_row [colIdx] - so_previous_row [colIdx];
376 count_current_row [colIdx + 1] = count_previous_row [colIdx + 1] + count_current_row [colIdx] - count_previous_row [colIdx];
377 if (std::isfinite (data[valIdx]))
379 current_row [colIdx + 1] += data[valIdx];
380 so_current_row [colIdx + 1] += data[valIdx] * data[valIdx];
381 ++(count_current_row [colIdx + 1]);
390 #endif // PCL_INTEGRAL_IMAGE2D_IMPL_H_