Point Cloud Library (PCL) 1.12.1
esf.hpp
1/*
2 * Software License Agreement (BSD License)
3 *
4 * Point Cloud Library (PCL) - www.pointclouds.org
5 * Copyright (c) 2010-2012, Willow Garage, Inc.
6 * Copyright (c) 2012-, Open Perception, Inc.
7 *
8 * All rights reserved.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 *
14 * * Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer.
16 * * Redistributions in binary form must reproduce the above
17 * copyright notice, this list of conditions and the following
18 * disclaimer in the documentation and/or other materials provided
19 * with the distribution.
20 * * Neither the name of the copyright holder(s) nor the names of its
21 * contributors may be used to endorse or promote products derived
22 * from this software without specific prior written permission.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
25 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
26 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
27 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
28 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
29 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
30 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
31 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
32 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
34 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
35 * POSSIBILITY OF SUCH DAMAGE.
36 *
37 * $Id: pfh.hpp 5027 2012-03-12 03:10:45Z rusu $
38 *
39 */
40
41#ifndef PCL_FEATURES_IMPL_ESF_H_
42#define PCL_FEATURES_IMPL_ESF_H_
43
44#include <pcl/features/esf.h>
46#include <pcl/common/transforms.h>
47#include <vector>
48#include <ctime> // for time
49
50//////////////////////////////////////////////////////////////////////////////////////////////////////////////////
51template <typename PointInT, typename PointOutT> void
53 PointCloudIn &pc, std::vector<float> &hist)
54{
55 const int binsize = 64;
56 unsigned int sample_size = 20000;
57 // @TODO: Replace with c++ stdlib uniform_random_generator
58 srand (static_cast<unsigned int> (time (nullptr)));
59 const auto maxindex = pc.size ();
60
61 std::vector<float> d2v, d1v, d3v, wt_d3;
62 std::vector<int> wt_d2;
63 d1v.reserve (sample_size);
64 d2v.reserve (sample_size * 3);
65 d3v.reserve (sample_size);
66 wt_d2.reserve (sample_size * 3);
67 wt_d3.reserve (sample_size);
68
69 float h_in[binsize] = {0};
70 float h_out[binsize] = {0};
71 float h_mix[binsize] = {0};
72 float h_mix_ratio[binsize] = {0};
73
74 float h_a3_in[binsize] = {0};
75 float h_a3_out[binsize] = {0};
76 float h_a3_mix[binsize] = {0};
77
78 float h_d3_in[binsize] = {0};
79 float h_d3_out[binsize] = {0};
80 float h_d3_mix[binsize] = {0};
81
82 float ratio=0.0;
83 float pih = static_cast<float>(M_PI) / 2.0f;
84 float a,b,c,s;
85 int th1,th2,th3;
86 int vxlcnt = 0;
87 int pcnt1,pcnt2,pcnt3;
88 for (std::size_t nn_idx = 0; nn_idx < sample_size; ++nn_idx)
89 {
90 // get a new random point
91 int index1 = rand()%maxindex;
92 int index2 = rand()%maxindex;
93 int index3 = rand()%maxindex;
94
95 if (index1==index2 || index1 == index3 || index2 == index3)
96 {
97 nn_idx--;
98 continue;
99 }
100
101 Eigen::Vector4f p1 = pc[index1].getVector4fMap ();
102 Eigen::Vector4f p2 = pc[index2].getVector4fMap ();
103 Eigen::Vector4f p3 = pc[index3].getVector4fMap ();
104
105 // A3
106 Eigen::Vector4f v21 (p2 - p1);
107 Eigen::Vector4f v31 (p3 - p1);
108 Eigen::Vector4f v23 (p2 - p3);
109 a = v21.norm (); b = v31.norm (); c = v23.norm (); s = (a+b+c) * 0.5f;
110 if (s * (s-a) * (s-b) * (s-c) <= 0.001f)
111 {
112 nn_idx--;
113 continue;
114 }
115
116 v21.normalize ();
117 v31.normalize ();
118 v23.normalize ();
119
120 //TODO: .dot gives nan's
121 th1 = static_cast<int> (pcl_round (std::acos (std::abs (v21.dot (v31))) / pih * (binsize-1)));
122 th2 = static_cast<int> (pcl_round (std::acos (std::abs (v23.dot (v31))) / pih * (binsize-1)));
123 th3 = static_cast<int> (pcl_round (std::acos (std::abs (v23.dot (v21))) / pih * (binsize-1)));
124 if (th1 < 0 || th1 >= binsize)
125 {
126 nn_idx--;
127 continue;
128 }
129 if (th2 < 0 || th2 >= binsize)
130 {
131 nn_idx--;
132 continue;
133 }
134 if (th3 < 0 || th3 >= binsize)
135 {
136 nn_idx--;
137 continue;
138 }
139
140 // D2
141 d2v.push_back (pcl::euclideanDistance (pc[index1], pc[index2]));
142 d2v.push_back (pcl::euclideanDistance (pc[index1], pc[index3]));
143 d2v.push_back (pcl::euclideanDistance (pc[index2], pc[index3]));
144
145 int vxlcnt_sum = 0;
146 int p_cnt = 0;
147 // IN, OUT, MIXED, Ratio line tracing, index1->index2
148 {
149 const int xs = p1[0] < 0.0? static_cast<int>(std::floor(p1[0])+GRIDSIZE_H): static_cast<int>(std::ceil(p1[0])+GRIDSIZE_H-1);
150 const int ys = p1[1] < 0.0? static_cast<int>(std::floor(p1[1])+GRIDSIZE_H): static_cast<int>(std::ceil(p1[1])+GRIDSIZE_H-1);
151 const int zs = p1[2] < 0.0? static_cast<int>(std::floor(p1[2])+GRIDSIZE_H): static_cast<int>(std::ceil(p1[2])+GRIDSIZE_H-1);
152 const int xt = p2[0] < 0.0? static_cast<int>(std::floor(p2[0])+GRIDSIZE_H): static_cast<int>(std::ceil(p2[0])+GRIDSIZE_H-1);
153 const int yt = p2[1] < 0.0? static_cast<int>(std::floor(p2[1])+GRIDSIZE_H): static_cast<int>(std::ceil(p2[1])+GRIDSIZE_H-1);
154 const int zt = p2[2] < 0.0? static_cast<int>(std::floor(p2[2])+GRIDSIZE_H): static_cast<int>(std::ceil(p2[2])+GRIDSIZE_H-1);
155 wt_d2.push_back (this->lci (xs, ys, zs, xt, yt, zt, ratio, vxlcnt, pcnt1));
156 if (wt_d2.back () == 2)
157 h_mix_ratio[static_cast<int> (pcl_round (ratio * (binsize-1)))]++;
158 vxlcnt_sum += vxlcnt;
159 p_cnt += pcnt1;
160 }
161 // IN, OUT, MIXED, Ratio line tracing, index1->index3
162 {
163 const int xs = p1[0] < 0.0? static_cast<int>(std::floor(p1[0])+GRIDSIZE_H): static_cast<int>(std::ceil(p1[0])+GRIDSIZE_H-1);
164 const int ys = p1[1] < 0.0? static_cast<int>(std::floor(p1[1])+GRIDSIZE_H): static_cast<int>(std::ceil(p1[1])+GRIDSIZE_H-1);
165 const int zs = p1[2] < 0.0? static_cast<int>(std::floor(p1[2])+GRIDSIZE_H): static_cast<int>(std::ceil(p1[2])+GRIDSIZE_H-1);
166 const int xt = p3[0] < 0.0? static_cast<int>(std::floor(p3[0])+GRIDSIZE_H): static_cast<int>(std::ceil(p3[0])+GRIDSIZE_H-1);
167 const int yt = p3[1] < 0.0? static_cast<int>(std::floor(p3[1])+GRIDSIZE_H): static_cast<int>(std::ceil(p3[1])+GRIDSIZE_H-1);
168 const int zt = p3[2] < 0.0? static_cast<int>(std::floor(p3[2])+GRIDSIZE_H): static_cast<int>(std::ceil(p3[2])+GRIDSIZE_H-1);
169 wt_d2.push_back (this->lci (xs, ys, zs, xt, yt, zt, ratio, vxlcnt, pcnt2));
170 if (wt_d2.back () == 2)
171 h_mix_ratio[static_cast<int>(pcl_round (ratio * (binsize-1)))]++;
172 vxlcnt_sum += vxlcnt;
173 p_cnt += pcnt2;
174 }
175 // IN, OUT, MIXED, Ratio line tracing, index2->index3
176 {
177 const int xs = p2[0] < 0.0? static_cast<int>(std::floor(p2[0])+GRIDSIZE_H): static_cast<int>(std::ceil(p2[0])+GRIDSIZE_H-1);
178 const int ys = p2[1] < 0.0? static_cast<int>(std::floor(p2[1])+GRIDSIZE_H): static_cast<int>(std::ceil(p2[1])+GRIDSIZE_H-1);
179 const int zs = p2[2] < 0.0? static_cast<int>(std::floor(p2[2])+GRIDSIZE_H): static_cast<int>(std::ceil(p2[2])+GRIDSIZE_H-1);
180 const int xt = p3[0] < 0.0? static_cast<int>(std::floor(p3[0])+GRIDSIZE_H): static_cast<int>(std::ceil(p3[0])+GRIDSIZE_H-1);
181 const int yt = p3[1] < 0.0? static_cast<int>(std::floor(p3[1])+GRIDSIZE_H): static_cast<int>(std::ceil(p3[1])+GRIDSIZE_H-1);
182 const int zt = p3[2] < 0.0? static_cast<int>(std::floor(p3[2])+GRIDSIZE_H): static_cast<int>(std::ceil(p3[2])+GRIDSIZE_H-1);
183 wt_d2.push_back (this->lci (xs,ys,zs,xt,yt,zt,ratio,vxlcnt,pcnt3));
184 if (wt_d2.back () == 2)
185 h_mix_ratio[static_cast<int>(pcl_round(ratio * (binsize-1)))]++;
186 vxlcnt_sum += vxlcnt;
187 p_cnt += pcnt3;
188 }
189
190 // D3 ( herons formula )
191 d3v.push_back (std::sqrt (std::sqrt (s * (s-a) * (s-b) * (s-c))));
192 if (vxlcnt_sum <= 21)
193 {
194 wt_d3.push_back (0);
195 h_a3_out[th1] += static_cast<float> (pcnt3) / 32.0f;
196 h_a3_out[th2] += static_cast<float> (pcnt1) / 32.0f;
197 h_a3_out[th3] += static_cast<float> (pcnt2) / 32.0f;
198 }
199 else
200 if (p_cnt - vxlcnt_sum < 4)
201 {
202 h_a3_in[th1] += static_cast<float> (pcnt3) / 32.0f;
203 h_a3_in[th2] += static_cast<float> (pcnt1) / 32.0f;
204 h_a3_in[th3] += static_cast<float> (pcnt2) / 32.0f;
205 wt_d3.push_back (1);
206 }
207 else
208 {
209 h_a3_mix[th1] += static_cast<float> (pcnt3) / 32.0f;
210 h_a3_mix[th2] += static_cast<float> (pcnt1) / 32.0f;
211 h_a3_mix[th3] += static_cast<float> (pcnt2) / 32.0f;
212 wt_d3.push_back (static_cast<float> (vxlcnt_sum) / static_cast<float> (p_cnt));
213 }
214 }
215 // Normalizing, get max
216 float maxd2 = 0;
217 float maxd3 = 0;
218
219 for (std::size_t nn_idx = 0; nn_idx < sample_size; ++nn_idx)
220 {
221 // get max of Dx
222 if (d2v[nn_idx] > maxd2)
223 maxd2 = d2v[nn_idx];
224 if (d2v[sample_size + nn_idx] > maxd2)
225 maxd2 = d2v[sample_size + nn_idx];
226 if (d2v[sample_size*2 +nn_idx] > maxd2)
227 maxd2 = d2v[sample_size*2 +nn_idx];
228 if (d3v[nn_idx] > maxd3)
229 maxd3 = d3v[nn_idx];
230 }
231
232 // Normalize and create histogram
233 int index;
234 for (std::size_t nn_idx = 0; nn_idx < sample_size; ++nn_idx)
235 {
236 if (wt_d3[nn_idx] >= 0.999) // IN
237 {
238 index = static_cast<int>(pcl_round (d3v[nn_idx] / maxd3 * (binsize-1)));
239 if (index >= 0 && index < binsize)
240 h_d3_in[index]++;
241 }
242 else
243 {
244 if (wt_d3[nn_idx] <= 0.001) // OUT
245 {
246 index = static_cast<int>(pcl_round (d3v[nn_idx] / maxd3 * (binsize-1)));
247 if (index >= 0 && index < binsize)
248 h_d3_out[index]++ ;
249 }
250 else
251 {
252 index = static_cast<int>(pcl_round (d3v[nn_idx] / maxd3 * (binsize-1)));
253 if (index >= 0 && index < binsize)
254 h_d3_mix[index]++;
255 }
256 }
257 }
258 //normalize and create histogram
259 for (std::size_t nn_idx = 0; nn_idx < d2v.size(); ++nn_idx )
260 {
261 if (wt_d2[nn_idx] == 0)
262 h_in[static_cast<int>(pcl_round (d2v[nn_idx] / maxd2 * (binsize-1)))]++ ;
263 if (wt_d2[nn_idx] == 1)
264 h_out[static_cast<int>(pcl_round (d2v[nn_idx] / maxd2 * (binsize-1)))]++;
265 if (wt_d2[nn_idx] == 2)
266 h_mix[static_cast<int>(pcl_round (d2v[nn_idx] / maxd2 * (binsize-1)))]++ ;
267 }
268
269 //float weights[10] = {1, 1, 1, 1, 1, 1, 1, 1 , 1 , 1};
270 float weights[10] = {0.5f, 0.5f, 0.5f, 0.5f, 0.5f, 1.0f, 1.0f, 2.0f, 2.0f, 2.0f};
271
272 hist.reserve (binsize * 10);
273 for (const float &i : h_a3_in)
274 hist.push_back (i * weights[0]);
275 for (const float &i : h_a3_out)
276 hist.push_back (i * weights[1]);
277 for (const float &i : h_a3_mix)
278 hist.push_back (i * weights[2]);
279
280 for (const float &i : h_d3_in)
281 hist.push_back (i * weights[3]);
282 for (const float &i : h_d3_out)
283 hist.push_back (i * weights[4]);
284 for (const float &i : h_d3_mix)
285 hist.push_back (i * weights[5]);
286
287 for (const float &i : h_in)
288 hist.push_back (i*0.5f * weights[6]);
289 for (const float &i : h_out)
290 hist.push_back (i * weights[7]);
291 for (const float &i : h_mix)
292 hist.push_back (i * weights[8]);
293 for (const float &i : h_mix_ratio)
294 hist.push_back (i*0.5f * weights[9]);
295
296 float sm = 0;
297 for (const float &i : hist)
298 sm += i;
299
300 for (float &i : hist)
301 i /= sm;
302}
303
304//////////////////////////////////////////////////////////////////////////////////////////////////////////////////
305template <typename PointInT, typename PointOutT> int
307 const int x1, const int y1, const int z1,
308 const int x2, const int y2, const int z2,
309 float &ratio, int &incnt, int &pointcount)
310{
311 int voxelcount = 0;
312 int voxel_in = 0;
313 int act_voxel[3];
314 act_voxel[0] = x1;
315 act_voxel[1] = y1;
316 act_voxel[2] = z1;
317 int x_inc, y_inc, z_inc;
318 int dx = x2 - x1;
319 int dy = y2 - y1;
320 int dz = z2 - z1;
321 if (dx < 0)
322 x_inc = -1;
323 else
324 x_inc = 1;
325 int l = std::abs (dx);
326 if (dy < 0)
327 y_inc = -1 ;
328 else
329 y_inc = 1;
330 int m = std::abs (dy);
331 if (dz < 0)
332 z_inc = -1 ;
333 else
334 z_inc = 1;
335 int n = std::abs (dz);
336 int dx2 = 2 * l;
337 int dy2 = 2 * m;
338 int dz2 = 2 * n;
339 if ((l >= m) & (l >= n))
340 {
341 int err_1 = dy2 - l;
342 int err_2 = dz2 - l;
343 for (int i = 1; i<l; i++)
344 {
345 voxelcount++;;
346 voxel_in += static_cast<int>(lut_[act_voxel[0]][act_voxel[1]][act_voxel[2]] == 1);
347 if (err_1 > 0)
348 {
349 act_voxel[1] += y_inc;
350 err_1 -= dx2;
351 }
352 if (err_2 > 0)
353 {
354 act_voxel[2] += z_inc;
355 err_2 -= dx2;
356 }
357 err_1 += dy2;
358 err_2 += dz2;
359 act_voxel[0] += x_inc;
360 }
361 }
362 else if ((m >= l) & (m >= n))
363 {
364 int err_1 = dx2 - m;
365 int err_2 = dz2 - m;
366 for (int i=1; i<m; i++)
367 {
368 voxelcount++;
369 voxel_in += static_cast<int>(lut_[act_voxel[0]][act_voxel[1]][act_voxel[2]] == 1);
370 if (err_1 > 0)
371 {
372 act_voxel[0] += x_inc;
373 err_1 -= dy2;
374 }
375 if (err_2 > 0)
376 {
377 act_voxel[2] += z_inc;
378 err_2 -= dy2;
379 }
380 err_1 += dx2;
381 err_2 += dz2;
382 act_voxel[1] += y_inc;
383 }
384 }
385 else
386 {
387 int err_1 = dy2 - n;
388 int err_2 = dx2 - n;
389 for (int i=1; i<n; i++)
390 {
391 voxelcount++;
392 voxel_in += static_cast<int>(lut_[act_voxel[0]][act_voxel[1]][act_voxel[2]] == 1);
393 if (err_1 > 0)
394 {
395 act_voxel[1] += y_inc;
396 err_1 -= dz2;
397 }
398 if (err_2 > 0)
399 {
400 act_voxel[0] += x_inc;
401 err_2 -= dz2;
402 }
403 err_1 += dy2;
404 err_2 += dx2;
405 act_voxel[2] += z_inc;
406 }
407 }
408 voxelcount++;
409 voxel_in += static_cast<int>(lut_[act_voxel[0]][act_voxel[1]][act_voxel[2]] == 1);
410 incnt = voxel_in;
411 pointcount = voxelcount;
412
413 if (voxel_in >= voxelcount-1)
414 return (0);
415
416 if (voxel_in <= 7)
417 return (1);
418
419 ratio = static_cast<float>(voxel_in) / static_cast<float>(voxelcount);
420 return (2);
421}
422
423//////////////////////////////////////////////////////////////////////////////////////////////////////////////////
424template <typename PointInT, typename PointOutT> void
426{
427 for (const auto& point: cluster)
428 {
429 int xx = point.x<0.0? static_cast<int>(std::floor(point.x)+GRIDSIZE_H) : static_cast<int>(std::ceil(point.x)+GRIDSIZE_H-1);
430 int yy = point.y<0.0? static_cast<int>(std::floor(point.y)+GRIDSIZE_H) : static_cast<int>(std::ceil(point.y)+GRIDSIZE_H-1);
431 int zz = point.z<0.0? static_cast<int>(std::floor(point.z)+GRIDSIZE_H) : static_cast<int>(std::ceil(point.z)+GRIDSIZE_H-1);
432
433 for (int x = -1; x < 2; x++)
434 for (int y = -1; y < 2; y++)
435 for (int z = -1; z < 2; z++)
436 {
437 int xi = xx + x;
438 int yi = yy + y;
439 int zi = zz + z;
440
441 if (yi >= GRIDSIZE || xi >= GRIDSIZE || zi>=GRIDSIZE || yi < 0 || xi < 0 || zi < 0)
442 {
443 ;
444 }
445 else
446 this->lut_[xi][yi][zi] = 1;
447 }
448 }
449}
450
451//////////////////////////////////////////////////////////////////////////////////////////////////////////////////
452template <typename PointInT, typename PointOutT> void
454{
455 for (const auto& point: cluster)
456 {
457 int xx = point.x<0.0? static_cast<int>(std::floor(point.x)+GRIDSIZE_H) : static_cast<int>(std::ceil(point.x)+GRIDSIZE_H-1);
458 int yy = point.y<0.0? static_cast<int>(std::floor(point.y)+GRIDSIZE_H) : static_cast<int>(std::ceil(point.y)+GRIDSIZE_H-1);
459 int zz = point.z<0.0? static_cast<int>(std::floor(point.z)+GRIDSIZE_H) : static_cast<int>(std::ceil(point.z)+GRIDSIZE_H-1);
460
461 for (int x = -1; x < 2; x++)
462 for (int y = -1; y < 2; y++)
463 for (int z = -1; z < 2; z++)
464 {
465 int xi = xx + x;
466 int yi = yy + y;
467 int zi = zz + z;
468
469 if (yi >= GRIDSIZE || xi >= GRIDSIZE || zi>=GRIDSIZE || yi < 0 || xi < 0 || zi < 0)
470 {
471 ;
472 }
473 else
474 this->lut_[xi][yi][zi] = 0;
475 }
476 }
477}
478
479//////////////////////////////////////////////////////////////////////////////////////////////////////////////////
480template <typename PointInT, typename PointOutT> void
482 const pcl::PointCloud<PointInT> &pc, float scalefactor, Eigen::Vector4f& centroid)
483{
484 pcl::compute3DCentroid (pc, centroid);
485 pcl::demeanPointCloud (pc, centroid, local_cloud_);
486
487 float max_distance = 0;
488 pcl::PointXYZ cog (0, 0, 0);
489
490 for (const auto& point: local_cloud_)
491 {
492 float d = pcl::euclideanDistance(cog,point);
493 if (d > max_distance)
494 max_distance = d;
495 }
496
497 float scale_factor = 1.0f / max_distance * scalefactor;
498
499 Eigen::Affine3f matrix = Eigen::Affine3f::Identity();
500 matrix.scale (scale_factor);
501 pcl::transformPointCloud (local_cloud_, local_cloud_, matrix);
502}
503
504//////////////////////////////////////////////////////////////////////////////////////////////
505template<typename PointInT, typename PointOutT> void
507{
509 {
510 output.width = output.height = 0;
511 output.clear ();
512 return;
513 }
514 // Copy the header
515 output.header = input_->header;
516
517 // Resize the output dataset
518 // Important! We should only allocate precisely how many elements we will need, otherwise
519 // we risk at pre-allocating too much memory which could lead to bad_alloc
520 // (see http://dev.pointclouds.org/issues/657)
521 output.width = output.height = 1;
522 output.is_dense = input_->is_dense;
523 output.resize (1);
524
525 // Perform the actual feature computation
526 computeFeature (output);
527
529}
530
531
532//////////////////////////////////////////////////////////////////////////////////////////////
533template <typename PointInT, typename PointOutT> void
535{
536 Eigen::Vector4f xyz_centroid;
537 std::vector<float> hist;
538 scale_points_unit_sphere (*surface_, static_cast<float>(GRIDSIZE_H), xyz_centroid);
539 this->voxelize9 (local_cloud_);
540 this->computeESF (local_cloud_, hist);
541 this->cleanup9 (local_cloud_);
542
543 // We only output _1_ signature
544 output.resize (1);
545 output.width = 1;
546 output.height = 1;
547
548 for (std::size_t d = 0; d < hist.size (); ++d)
549 output[0].histogram[d] = hist[d];
550}
551
552#define PCL_INSTANTIATE_ESFEstimation(T,OutT) template class PCL_EXPORTS pcl::ESFEstimation<T,OutT>;
553
554#endif // PCL_FEATURES_IMPL_ESF_H_
555
void compute(PointCloudOut &output)
Overloaded computed method from pcl::Feature.
Definition: esf.hpp:506
void computeESF(PointCloudIn &pc, std::vector< float > &hist)
...
Definition: esf.hpp:52
typename Feature< PointInT, PointOutT >::PointCloudOut PointCloudOut
Definition: esf.h:74
void voxelize9(PointCloudIn &cluster)
...
Definition: esf.hpp:425
void scale_points_unit_sphere(const pcl::PointCloud< PointInT > &pc, float scalefactor, Eigen::Vector4f &centroid)
...
Definition: esf.hpp:481
int lci(const int x1, const int y1, const int z1, const int x2, const int y2, const int z2, float &ratio, int &incnt, int &pointcount)
...
Definition: esf.hpp:306
void cleanup9(PointCloudIn &cluster)
...
Definition: esf.hpp:453
void computeFeature(PointCloudOut &output) override
Estimate the Ensebmel of Shape Function (ESF) descriptors at a set of points given by <setInputCloud ...
Definition: esf.hpp:534
Feature represents the base feature class.
Definition: feature.h:107
std::size_t size() const
Definition: point_cloud.h:443
Define standard C methods to do distance calculations.
void demeanPointCloud(ConstCloudIterator< PointT > &cloud_iterator, const Eigen::Matrix< Scalar, 4, 1 > &centroid, pcl::PointCloud< PointT > &cloud_out, int npts=0)
Subtract a centroid from a point cloud and return the de-meaned representation.
Definition: centroid.hpp:640
void transformPointCloud(const pcl::PointCloud< PointT > &cloud_in, pcl::PointCloud< PointT > &cloud_out, const Eigen::Matrix< Scalar, 4, 4 > &transform, bool copy_all_fields)
Apply a rigid transform defined by a 4x4 matrix.
Definition: transforms.hpp:221
unsigned int compute3DCentroid(ConstCloudIterator< PointT > &cloud_iterator, Eigen::Matrix< Scalar, 4, 1 > &centroid)
Compute the 3D (X-Y-Z) centroid of a set of points and return it as a 3D vector.
Definition: centroid.hpp:56
float euclideanDistance(const PointType1 &p1, const PointType2 &p2)
Calculate the euclidean distance between the two given points.
Definition: distances.h:204
__inline double pcl_round(double number)
Win32 doesn't seem to have rounding functions.
Definition: pcl_macros.h:239
#define M_PI
Definition: pcl_macros.h:201
A point structure representing Euclidean xyz coordinates.