Point Cloud Library (PCL)  1.14.0-dev
conditional_removal.hpp
1 /*
2  * Software License Agreement (BSD License)
3  *
4  * Copyright (c) 2010, Willow Garage, Inc.
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *
11  * * Redistributions of source code must retain the above copyright
12  * notice, this list of conditions and the following disclaimer.
13  * * Redistributions in binary form must reproduce the above
14  * copyright notice, this list of conditions and the following
15  * disclaimer in the documentation and/or other materials provided
16  * with the distribution.
17  * * Neither the name of the copyright holder(s) nor the names of its
18  * contributors may be used to endorse or promote products derived
19  * from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
25  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
27  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
29  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
31  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32  * POSSIBILITY OF SUCH DAMAGE.
33  *
34  * $Id$
35  *
36  */
37 
38 #ifndef PCL_FILTER_IMPL_FIELD_VAL_CONDITION_H_
39 #define PCL_FILTER_IMPL_FIELD_VAL_CONDITION_H_
40 
41 #include <pcl/common/io.h>
42 #include <pcl/common/copy_point.h>
43 #include <pcl/filters/conditional_removal.h>
44 
45 //////////////////////////////////////////////////////////////////////////
46 //////////////////////////////////////////////////////////////////////////
47 //////////////////////////////////////////////////////////////////////////
48 template <typename PointT>
50  const std::string &field_name, ComparisonOps::CompareOp op, double compare_val)
52  , compare_val_ (compare_val), point_data_ (nullptr)
53 {
54  field_name_ = field_name;
55  op_ = op;
56 
57  // Get all fields
58  const auto point_fields = pcl::getFields<PointT> ();
59 
60  // Find field_name
61  if (point_fields.empty ())
62  {
63  PCL_WARN ("[pcl::FieldComparison::FieldComparison] no fields found!\n");
64  capable_ = false;
65  return;
66  }
67 
68  // Get the field index
69  std::size_t d;
70  for (d = 0; d < point_fields.size (); ++d)
71  {
72  if (point_fields[d].name == field_name)
73  break;
74  }
75 
76  if (d == point_fields.size ())
77  {
78  PCL_WARN ("[pcl::FieldComparison::FieldComparison] field not found!\n");
79  capable_ = false;
80  return;
81  }
82  std::uint8_t datatype = point_fields[d].datatype;
83  std::uint32_t offset = point_fields[d].offset;
84 
85  point_data_ = new PointDataAtOffset<PointT>(datatype, offset);
86  capable_ = true;
87 }
88 
89 //////////////////////////////////////////////////////////////////////////
90 template <typename PointT>
92 {
93  delete point_data_;
94 }
95 
96 //////////////////////////////////////////////////////////////////////////
97 template <typename PointT> bool
99 {
100  if (!this->capable_)
101  {
102  PCL_WARN ("[pcl::FieldComparison::evaluate] invalid comparison!\n");
103  return (false);
104  }
105 
106  // if p(data) > val then compare_result = 1
107  // if p(data) == val then compare_result = 0
108  // if p(data) < ival then compare_result = -1
109  int compare_result = point_data_->compare (point, compare_val_);
110 
111  switch (this->op_)
112  {
114  return (compare_result > 0);
116  return (compare_result >= 0);
118  return (compare_result < 0);
120  return (compare_result <= 0);
122  return (compare_result == 0);
123  default:
124  PCL_WARN ("[pcl::FieldComparison::evaluate] unrecognized op_!\n");
125  return (false);
126  }
127 }
128 
129 //////////////////////////////////////////////////////////////////////////
130 //////////////////////////////////////////////////////////////////////////
131 //////////////////////////////////////////////////////////////////////////
132 template <typename PointT>
134  const std::string &component_name, ComparisonOps::CompareOp op, double compare_val) :
135  component_name_ (component_name), component_offset_ (), compare_val_ (compare_val)
136 {
137  // get all the fields
138  const auto point_fields = pcl::getFields<PointT> ();
139 
140  // Locate the "rgb" field
141  std::size_t d;
142  for (d = 0; d < point_fields.size (); ++d)
143  {
144  if (point_fields[d].name == "rgb" || point_fields[d].name == "rgba")
145  break;
146  }
147  if (d == point_fields.size ())
148  {
149  PCL_WARN ("[pcl::PackedRGBComparison::PackedRGBComparison] rgb field not found!\n");
150  capable_ = false;
151  return;
152  }
153 
154  // Verify the datatype
155  std::uint8_t datatype = point_fields[d].datatype;
156  if (datatype != pcl::PCLPointField::FLOAT32 &&
157  datatype != pcl::PCLPointField::UINT32 &&
158  datatype != pcl::PCLPointField::INT32)
159  {
160  PCL_WARN ("[pcl::PackedRGBComparison::PackedRGBComparison] has unusable type!\n");
161  capable_ = false;
162  return;
163  }
164 
165  // Verify the component name
166  if (component_name == "r")
167  {
168  component_offset_ = point_fields[d].offset + 2;
169  }
170  else if (component_name == "g")
171  {
172  component_offset_ = point_fields[d].offset + 1;
173  }
174  else if (component_name == "b")
175  {
176  component_offset_ = point_fields[d].offset;
177  }
178  else
179  {
180  PCL_WARN ("[pcl::PackedRGBComparison::PackedRGBComparison] unrecognized component name!\n");
181  capable_ = false;
182  return;
183  }
184 
185  // save the rest of the context
186  capable_ = true;
187  op_ = op;
188 }
189 
190 
191 //////////////////////////////////////////////////////////////////////////
192 template <typename PointT> bool
194 {
195  // extract the component value
196  const auto* pt_data = reinterpret_cast<const std::uint8_t*> (&point);
197  std::uint8_t my_val = *(pt_data + component_offset_);
198 
199  // now do the comparison
200  switch (this->op_)
201  {
203  return (my_val > this->compare_val_);
205  return (my_val >= this->compare_val_);
207  return (my_val < this->compare_val_);
209  return (my_val <= this->compare_val_);
211  return (my_val == this->compare_val_);
212  default:
213  PCL_WARN ("[pcl::PackedRGBComparison::evaluate] unrecognized op_!\n");
214  return (false);
215  }
216 }
217 
218 //////////////////////////////////////////////////////////////////////////
219 //////////////////////////////////////////////////////////////////////////
220 //////////////////////////////////////////////////////////////////////////
221 template <typename PointT>
223  const std::string &component_name, ComparisonOps::CompareOp op, double compare_val) :
224  component_name_ (component_name), component_id_ (), compare_val_ (compare_val), rgb_offset_ ()
225 {
226  // Get all the fields
227  const auto point_fields = pcl::getFields<PointT> ();
228 
229  // Locate the "rgb" field
230  std::size_t d;
231  for (d = 0; d < point_fields.size (); ++d)
232  if (point_fields[d].name == "rgb" || point_fields[d].name == "rgba")
233  break;
234  if (d == point_fields.size ())
235  {
236  PCL_WARN ("[pcl::PackedHSIComparison::PackedHSIComparison] rgb field not found!\n");
237  capable_ = false;
238  return;
239  }
240 
241  // Verify the datatype
242  std::uint8_t datatype = point_fields[d].datatype;
243  if (datatype != pcl::PCLPointField::FLOAT32 &&
244  datatype != pcl::PCLPointField::UINT32 &&
245  datatype != pcl::PCLPointField::INT32)
246  {
247  PCL_WARN ("[pcl::PackedHSIComparison::PackedHSIComparison] has unusable type!\n");
248  capable_ = false;
249  return;
250  }
251 
252  // verify the offset
253  std::uint32_t offset = point_fields[d].offset;
254  if (offset % 4 != 0)
255  {
256  PCL_WARN ("[pcl::PackedHSIComparison::PackedHSIComparison] rgb field is not 32 bit aligned!\n");
257  capable_ = false;
258  return;
259  }
260  rgb_offset_ = point_fields[d].offset;
261 
262  // verify the component name
263  if (component_name == "h" )
264  {
265  component_id_ = H;
266  }
267  else if (component_name == "s")
268  {
269  component_id_ = S;
270  }
271  else if (component_name == "i")
272  {
273  component_id_ = I;
274  }
275  else
276  {
277  PCL_WARN ("[pcl::PackedHSIComparison::PackedHSIComparison] unrecognized component name!\n");
278  capable_ = false;
279  return;
280  }
281 
282  // Save the context
283  capable_ = true;
284  op_ = op;
285 }
286 
287 //////////////////////////////////////////////////////////////////////////
288 template <typename PointT> bool
290 {
291  // Since this is a const function, we can't make these data members because we change them here
292  static std::uint32_t rgb_val_ = 0;
293  static std::uint8_t r_ = 0;
294  static std::uint8_t g_ = 0;
295  static std::uint8_t b_ = 0;
296  static std::int8_t h_ = 0;
297  static std::uint8_t s_ = 0;
298  static std::uint8_t i_ = 0;
299 
300  // We know that rgb data is 32 bit aligned (verified in the ctor) so...
301  const auto* pt_data = reinterpret_cast<const std::uint8_t*> (&point);
302  const auto* rgb_data = reinterpret_cast<const std::uint32_t*> (pt_data + rgb_offset_);
303  std::uint32_t new_rgb_val = *rgb_data;
304 
305  if (rgb_val_ != new_rgb_val)
306  { // avoid having to redo this calc, if possible
307  rgb_val_ = new_rgb_val;
308  // extract r,g,b
309  r_ = static_cast <std::uint8_t> (rgb_val_ >> 16);
310  g_ = static_cast <std::uint8_t> (rgb_val_ >> 8);
311  b_ = static_cast <std::uint8_t> (rgb_val_);
312 
313  // definitions taken from https://en.wikipedia.org/wiki/HSL_and_HSI
314  float hx = (2.0f * r_ - g_ - b_) / 4.0f; // hue x component -127 to 127
315  float hy = static_cast<float> (g_ - b_) * 111.0f / 255.0f; // hue y component -111 to 111
316  h_ = static_cast<std::int8_t> (std::atan2(hy, hx) * 128.0f / M_PI);
317 
318  std::int32_t i = (r_+g_+b_)/3; // 0 to 255
319  i_ = static_cast<std::uint8_t> (i);
320 
321  std::int32_t m; // min(r,g,b)
322  m = (r_ < g_) ? r_ : g_;
323  m = (m < b_) ? m : b_;
324 
325  s_ = static_cast<std::uint8_t> ((i == 0) ? 0 : 255 - (m * 255) / i); // saturation 0 to 255
326  }
327 
328  float my_val = 0;
329 
330  switch (component_id_)
331  {
332  case H:
333  my_val = static_cast <float> (h_);
334  break;
335  case S:
336  my_val = static_cast <float> (s_);
337  break;
338  case I:
339  my_val = static_cast <float> (i_);
340  break;
341  default:
342  assert (false);
343  }
344 
345  // now do the comparison
346  switch (this->op_)
347  {
349  return (my_val > this->compare_val_);
351  return (my_val >= this->compare_val_);
353  return (my_val < this->compare_val_);
355  return (my_val <= this->compare_val_);
357  return (my_val == this->compare_val_);
358  default:
359  PCL_WARN ("[pcl::PackedHSIComparison::evaluate] unrecognized op_!\n");
360  return (false);
361  }
362 }
363 
364 
365 //////////////////////////////////////////////////////////////////////////
366 //////////////////////////////////////////////////////////////////////////
367 //////////////////////////////////////////////////////////////////////////
368 template<typename PointT>
370  comp_scalar_ (0.0)
371 {
372  // get all the fields
373  const auto point_fields = pcl::getFields<PointT> ();
374 
375  // Locate the "x" field
376  std::size_t dX;
377  for (dX = 0; dX < point_fields.size (); ++dX)
378  {
379  if (point_fields[dX].name == "x")
380  break;
381  }
382  if (dX == point_fields.size ())
383  {
384  PCL_WARN ("[pcl::TfQuadraticXYZComparison::TfQuadraticXYZComparison] x field not found!\n");
385  capable_ = false;
386  return;
387  }
388 
389  // Locate the "y" field
390  std::size_t dY;
391  for (dY = 0; dY < point_fields.size (); ++dY)
392  {
393  if (point_fields[dY].name == "y")
394  break;
395  }
396  if (dY == point_fields.size ())
397  {
398  PCL_WARN ("[pcl::TfQuadraticXYZComparison::TfQuadraticXYZComparison] y field not found!\n");
399  capable_ = false;
400  return;
401  }
402 
403  // Locate the "z" field
404  std::size_t dZ;
405  for (dZ = 0; dZ < point_fields.size (); ++dZ)
406  {
407  if (point_fields[dZ].name == "z")
408  break;
409  }
410  if (dZ == point_fields.size ())
411  {
412  PCL_WARN ("[pcl::TfQuadraticXYZComparison::TfQuadraticXYZComparison] z field not found!\n");
413  capable_ = false;
414  return;
415  }
416 
417  comp_matr_ << 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 1.0;
418  comp_vect_ << 0.0, 0.0, 0.0, 1.0;
419  tf_comp_matr_ = comp_matr_;
420  tf_comp_vect_ = comp_vect_;
422  capable_ = true;
423 }
424 
425 //////////////////////////////////////////////////////////////////////////
426 template<typename PointT>
428  const Eigen::Matrix3f &comparison_matrix,
429  const Eigen::Vector3f &comparison_vector,
430  const float &comparison_scalar,
431  const Eigen::Affine3f &comparison_transform) :
432  comp_scalar_ (comparison_scalar)
433 {
434  // get all the fields
435  const auto point_fields = pcl::getFields<PointT> ();
436 
437  // Locate the "x" field
438  std::size_t dX;
439  for (dX = 0; dX < point_fields.size (); ++dX)
440  {
441  if (point_fields[dX].name == "x")
442  break;
443  }
444  if (dX == point_fields.size ())
445  {
446  PCL_WARN ("[pcl::TfQuadraticXYZComparison::TfQuadraticXYZComparison] x field not found!\n");
447  capable_ = false;
448  return;
449  }
450 
451  // Locate the "y" field
452  std::size_t dY;
453  for (dY = 0; dY < point_fields.size (); ++dY)
454  {
455  if (point_fields[dY].name == "y")
456  break;
457  }
458  if (dY == point_fields.size ())
459  {
460  PCL_WARN ("[pcl::TfQuadraticXYZComparison::TfQuadraticXYZComparison] y field not found!\n");
461  capable_ = false;
462  return;
463  }
464 
465  // Locate the "z" field
466  std::size_t dZ;
467  for (dZ = 0; dZ < point_fields.size (); ++dZ)
468  {
469  if (point_fields[dZ].name == "z")
470  break;
471  }
472  if (dZ == point_fields.size ())
473  {
474  PCL_WARN ("[pcl::TfQuadraticXYZComparison::TfQuadraticXYZComparison] z field not found!\n");
475  capable_ = false;
476  return;
477  }
478 
479  capable_ = true;
480  op_ = op;
481  setComparisonMatrix (comparison_matrix);
482  setComparisonVector (comparison_vector);
483  if (!comparison_transform.matrix ().isIdentity ())
484  transformComparison (comparison_transform);
485 }
486 
487 //////////////////////////////////////////////////////////////////////////
488 template<typename PointT>
489 bool
491 {
492  Eigen::Vector4f pointAffine;
493  pointAffine << point.x, point.y, point.z, 1;
494 
495  float myVal = static_cast<float>(2.0f * tf_comp_vect_.transpose () * pointAffine) + static_cast<float>(pointAffine.transpose () * tf_comp_matr_ * pointAffine) + comp_scalar_ - 3.0f;
496 
497  // now do the comparison
498  switch (this->op_)
499  {
501  return (myVal > 0);
503  return (myVal >= 0);
505  return (myVal < 0);
507  return (myVal <= 0);
509  return (myVal == 0);
510  default:
511  PCL_WARN ("[pcl::TfQuadraticXYZComparison::evaluate] unrecognized op_!\n");
512  return (false);
513  }
514 }
515 
516 //////////////////////////////////////////////////////////////////////////
517 //////////////////////////////////////////////////////////////////////////
518 //////////////////////////////////////////////////////////////////////////
519 template <typename PointT> int
520 pcl::PointDataAtOffset<PointT>::compare (const PointT& p, const double& val)
521 {
522  // if p(data) > val return 1
523  // if p(data) == val return 0
524  // if p(data) < val return -1
525 
526  const auto* pt_data = reinterpret_cast<const std::uint8_t*> (&p);
527 
528 #define SAFE_COMPARE(CASE_LABEL) \
529  case CASE_LABEL: { \
530  pcl::traits::asType_t<CASE_LABEL> pt_val; \
531  memcpy(&pt_val, pt_data + this->offset_, sizeof(pt_val)); \
532  return (pt_val > static_cast<pcl::traits::asType_t<(CASE_LABEL)>>(val)) - \
533  (pt_val < static_cast<pcl::traits::asType_t<(CASE_LABEL)>>(val)); \
534  }
535 
536  switch (datatype_)
537  {
538  SAFE_COMPARE(pcl::PCLPointField::BOOL)
539  SAFE_COMPARE(pcl::PCLPointField::INT8)
540  SAFE_COMPARE(pcl::PCLPointField::UINT8)
541  SAFE_COMPARE(pcl::PCLPointField::INT16)
542  SAFE_COMPARE(pcl::PCLPointField::UINT16)
543  SAFE_COMPARE(pcl::PCLPointField::INT32)
544  SAFE_COMPARE(pcl::PCLPointField::UINT32)
545  SAFE_COMPARE(pcl::PCLPointField::INT64)
546  SAFE_COMPARE(pcl::PCLPointField::UINT64)
547  SAFE_COMPARE(pcl::PCLPointField::FLOAT32)
548  SAFE_COMPARE(pcl::PCLPointField::FLOAT64)
549 
550  default :
551  PCL_WARN ("[pcl::PointDataAtOffset::compare] unknown data_type!\n");
552  return (0);
553  }
554 #undef SAFE_COMPARE
555 }
556 
557 //////////////////////////////////////////////////////////////////////////
558 //////////////////////////////////////////////////////////////////////////
559 //////////////////////////////////////////////////////////////////////////
560 template <typename PointT> void
562 {
563  if (!comparison->isCapable ())
564  capable_ = false;
565  comparisons_.push_back (comparison);
566 }
567 
568 //////////////////////////////////////////////////////////////////////////
569 template <typename PointT> void
571 {
572  if (!condition->isCapable ())
573  capable_ = false;
574  conditions_.push_back (condition);
575 }
576 
577 //////////////////////////////////////////////////////////////////////////
578 //////////////////////////////////////////////////////////////////////////
579 //////////////////////////////////////////////////////////////////////////
580 template <typename PointT> bool
582 {
583  for (std::size_t i = 0; i < comparisons_.size (); ++i)
584  if (!comparisons_[i]->evaluate (point))
585  return (false);
586 
587  for (std::size_t i = 0; i < conditions_.size (); ++i)
588  if (!conditions_[i]->evaluate (point))
589  return (false);
590 
591  return (true);
592 }
593 
594 //////////////////////////////////////////////////////////////////////////
595 //////////////////////////////////////////////////////////////////////////
596 //////////////////////////////////////////////////////////////////////////
597 template <typename PointT> bool
599 {
600  if (comparisons_.empty () && conditions_.empty ())
601  return (true);
602  for (std::size_t i = 0; i < comparisons_.size (); ++i)
603  if (comparisons_[i]->evaluate(point))
604  return (true);
605 
606  for (std::size_t i = 0; i < conditions_.size (); ++i)
607  if (conditions_[i]->evaluate (point))
608  return (true);
609 
610  return (false);
611 }
612 
613 //////////////////////////////////////////////////////////////////////////
614 //////////////////////////////////////////////////////////////////////////
615 //////////////////////////////////////////////////////////////////////////
616 template <typename PointT> void
618 {
619  condition_ = condition;
620  capable_ = condition_->isCapable ();
621 }
622 
623 //////////////////////////////////////////////////////////////////////////
624 template <typename PointT> void
626 {
627  if (!capable_)
628  {
629  PCL_WARN ("[pcl::%s::applyFilter] not capable!\n", getClassName ().c_str ());
630  return;
631  }
632  // Has the input dataset been set already?
633  if (!input_)
634  {
635  PCL_WARN ("[pcl::%s::applyFilter] No input dataset given!\n", getClassName ().c_str ());
636  return;
637  }
638 
639  if (condition_.get () == nullptr)
640  {
641  PCL_WARN ("[pcl::%s::applyFilter] No filtering condition given!\n", getClassName ().c_str ());
642  return;
643  }
644 
645  // Copy the header (and thus the frame_id) + allocate enough space for points
646  output.header = input_->header;
647  if (!keep_organized_)
648  {
649  output.height = 1; // filtering breaks the organized structure
650  output.is_dense = true;
651  }
652  else
653  {
654  output.height = this->input_->height;
655  output.width = this->input_->width;
656  output.is_dense = this->input_->is_dense;
657  }
658  output.resize (input_->size ());
659  removed_indices_->resize (input_->size ());
660 
661  int nr_removed_p = 0;
662 
663  if (!keep_organized_)
664  {
665  int nr_p = 0;
666  for (std::size_t index: (*Filter<PointT>::indices_))
667  {
668 
669  const PointT& point = (*input_)[index];
670  // Check if the point is invalid
671  if (!std::isfinite (point.x)
672  || !std::isfinite (point.y)
673  || !std::isfinite (point.z))
674  {
675  if (extract_removed_indices_)
676  {
677  (*removed_indices_)[nr_removed_p] = index;
678  nr_removed_p++;
679  }
680  continue;
681  }
682 
683  if (condition_->evaluate (point))
684  {
685  copyPoint (point, output[nr_p]);
686  nr_p++;
687  }
688  else
689  {
690  if (extract_removed_indices_)
691  {
692  (*removed_indices_)[nr_removed_p] = index;
693  nr_removed_p++;
694  }
695  }
696  }
697 
698  output.width = nr_p;
699  output.resize (nr_p);
700  }
701  else
702  {
704  std::sort (indices.begin (), indices.end ()); //TODO: is this necessary or can we assume the indices to be sorted?
705  bool removed_p = false;
706  std::size_t ci = 0;
707  for (std::size_t cp = 0; cp < input_->size (); ++cp)
708  {
709  if (cp == static_cast<std::size_t> (indices[ci]))
710  {
711  if (ci < indices.size () - 1)
712  {
713  ci++;
714  if (cp == static_cast<std::size_t> (indices[ci])) //check whether the next index will have the same value. TODO: necessary?
715  continue;
716  }
717 
718  // copy all the fields
719  copyPoint ((*input_)[cp], output[cp]);
720 
721  if (!condition_->evaluate ((*input_)[cp]))
722  {
723  output[cp].getVector4fMap ().setConstant (user_filter_value_);
724  removed_p = true;
725 
726  if (extract_removed_indices_)
727  {
728  (*removed_indices_)[nr_removed_p] = static_cast<int> (cp);
729  nr_removed_p++;
730  }
731  }
732  }
733  else
734  {
735  output[cp].getVector4fMap ().setConstant (user_filter_value_);
736  removed_p = true;
737  //as for !keep_organized_: removed points due to setIndices are not considered as removed_indices_
738  }
739  }
740 
741  if (removed_p && !std::isfinite (user_filter_value_))
742  output.is_dense = false;
743  }
744  removed_indices_->resize (nr_removed_p);
745 }
746 
747 #define PCL_INSTANTIATE_PointDataAtOffset(T) template class PCL_EXPORTS pcl::PointDataAtOffset<T>;
748 #define PCL_INSTANTIATE_ComparisonBase(T) template class PCL_EXPORTS pcl::ComparisonBase<T>;
749 #define PCL_INSTANTIATE_FieldComparison(T) template class PCL_EXPORTS pcl::FieldComparison<T>;
750 #define PCL_INSTANTIATE_PackedRGBComparison(T) template class PCL_EXPORTS pcl::PackedRGBComparison<T>;
751 #define PCL_INSTANTIATE_PackedHSIComparison(T) template class PCL_EXPORTS pcl::PackedHSIComparison<T>;
752 #define PCL_INSTANTIATE_TfQuadraticXYZComparison(T) template class PCL_EXPORTS pcl::TfQuadraticXYZComparison<T>;
753 #define PCL_INSTANTIATE_ConditionBase(T) template class PCL_EXPORTS pcl::ConditionBase<T>;
754 #define PCL_INSTANTIATE_ConditionAnd(T) template class PCL_EXPORTS pcl::ConditionAnd<T>;
755 #define PCL_INSTANTIATE_ConditionOr(T) template class PCL_EXPORTS pcl::ConditionOr<T>;
756 #define PCL_INSTANTIATE_ConditionalRemoval(T) template class PCL_EXPORTS pcl::ConditionalRemoval<T>;
757 
758 #endif
The (abstract) base class for the comparison object.
ComparisonOps::CompareOp op_
The comparison operator type.
bool capable_
True if capable.
std::string field_name_
Field name to compare data on.
bool evaluate(const PointT &point) const override
Determine if a point meets this condition.
void addCondition(Ptr condition)
Add a nested condition to this condition.
typename ComparisonBase::ConstPtr ComparisonBaseConstPtr
void addComparison(ComparisonBaseConstPtr comparison)
Add a new comparison.
shared_ptr< ConditionBase< PointT > > Ptr
bool evaluate(const PointT &point) const override
Determine if a point meets this condition.
void applyFilter(PointCloud &output) override
Filter a Point Cloud.
void setCondition(ConditionBasePtr condition)
Set the condition that the filter will use.
typename ConditionBase::Ptr ConditionBasePtr
The field-based specialization of the comparison object.
~FieldComparison() override
Destructor.
PointDataAtOffset< PointT > * point_data_
The point data to compare.
bool evaluate(const PointT &point) const override
Determine the result of this comparison.
Filter represents the base filter class.
Definition: filter.h:81
A packed HSI specialization of the comparison object.
std::uint32_t rgb_offset_
The offset of the component.
bool evaluate(const PointT &point) const override
Determine the result of this comparison.
ComponentId component_id_
The ID of the component.
A packed rgb specialization of the comparison object.
bool evaluate(const PointT &point) const override
Determine the result of this comparison.
std::uint32_t component_offset_
The offset of the component.
PointCloud represents the base class in PCL for storing collections of 3D points.
Definition: point_cloud.h:173
bool is_dense
True if no points are invalid (e.g., have NaN or Inf values in any of their floating point fields).
Definition: point_cloud.h:403
void resize(std::size_t count)
Resizes the container to contain count elements.
Definition: point_cloud.h:462
std::uint32_t width
The point cloud width (if organized as an image-structure).
Definition: point_cloud.h:398
pcl::PCLHeader header
The point cloud header.
Definition: point_cloud.h:392
std::uint32_t height
The point cloud height (if organized as an image-structure).
Definition: point_cloud.h:400
A datatype that enables type-correct comparisons.
int compare(const PointT &p, const double &val)
Compare function.
void setComparisonVector(const Eigen::Vector3f &vector)
set the vector "v" of the comparison "p'Ap + 2v'p + c [OP] 0".
void transformComparison(const Eigen::Matrix4f &transform)
transform the coordinate system of the comparison.
void setComparisonMatrix(const Eigen::Matrix3f &matrix)
set the matrix "A" of the comparison "p'Ap + 2v'p + c [OP] 0".
bool evaluate(const PointT &point) const override
Determine the result of this comparison.
void copyPoint(const PointInT &point_in, PointOutT &point_out)
Copy the fields of a source point into a target point.
Definition: copy_point.hpp:137
CompareOp
The kind of comparison operations that are possible within a comparison object.
IndicesAllocator<> Indices
Type used for indices in PCL.
Definition: types.h:133
#define M_PI
Definition: pcl_macros.h:201
A point structure representing Euclidean xyz coordinates, and the RGB color.