38 #ifndef PCL_FILTERS_IMPL_CROP_HULL_H_
39 #define PCL_FILTERS_IMPL_CROP_HULL_H_
41 #include <pcl/filters/crop_hull.h>
45 template<
typename Po
intT>
void
49 removed_indices_->clear();
50 indices.reserve(indices_->size());
51 removed_indices_->reserve(indices_->size());
59 const Eigen::Vector3f range = getHullCloudRange ();
60 if (range[0] <= range[1] && range[0] <= range[2])
61 applyFilter2D<1,2> (indices);
62 else if (range[1] <= range[2] && range[1] <= range[0])
63 applyFilter2D<2,0> (indices);
65 applyFilter2D<0,1> (indices);
69 applyFilter3D (indices);
74 template<
typename Po
intT> Eigen::Vector3f
77 Eigen::Vector3f cloud_min (
78 std::numeric_limits<float>::max (),
79 std::numeric_limits<float>::max (),
80 std::numeric_limits<float>::max ()
82 Eigen::Vector3f cloud_max (
83 -std::numeric_limits<float>::max (),
84 -std::numeric_limits<float>::max (),
85 -std::numeric_limits<float>::max ()
89 for (
auto const & idx : poly.vertices)
91 Eigen::Vector3f pt = (*hull_cloud_)[idx].getVector3fMap ();
92 cloud_min = cloud_min.cwiseMin(pt);
93 cloud_max = cloud_max.cwiseMax(pt);
97 return (cloud_max - cloud_min);
101 template<
typename Po
intT>
template<
unsigned PlaneDim1,
unsigned PlaneDim2>
void
104 for (std::size_t index = 0; index < indices_->size (); index++)
109 for (poly = 0; poly < hull_polygons_.size (); poly++)
111 if (isPointIn2DPolyWithVertIndices<PlaneDim1,PlaneDim2> (
112 (*input_)[(*indices_)[index]], hull_polygons_[poly], *hull_cloud_
116 indices.push_back ((*indices_)[index]);
124 if (poly == hull_polygons_.size () && !crop_outside_)
125 indices.push_back ((*indices_)[index]);
126 if (indices.empty() || indices.back() != (*indices_)[index]) {
127 removed_indices_->push_back ((*indices_)[index]);
133 template<
typename Po
intT>
void
139 for (std::size_t index = 0; index < indices_->size (); index++)
148 std::size_t crossings[3] = {0,0,0};
149 Eigen::Vector3f rays[3] =
151 Eigen::Vector3f(0.264882f, 0.688399f, 0.675237f),
152 Eigen::Vector3f(0.0145419f, 0.732901f, 0.68018f),
153 Eigen::Vector3f(0.856514f, 0.508771f, 0.0868081f)
156 for (
const auto & hull_polygon : hull_polygons_)
157 for (std::size_t ray = 0; ray < 3; ray++)
158 crossings[ray] += rayTriangleIntersect
159 ((*input_)[(*indices_)[index]], rays[ray], hull_polygon, *hull_cloud_);
161 bool crosses = (crossings[0]&1) + (crossings[1]&1) + (crossings[2]&1) > 1;
162 if ((crop_outside_ && crosses) || (!crop_outside_ && !crosses))
163 indices.push_back ((*indices_)[index]);
165 removed_indices_->push_back ((*indices_)[index]);
170 template<
typename Po
intT>
template<
unsigned PlaneDim1,
unsigned PlaneDim2>
bool
174 bool in_poly =
false;
175 double x1, x2, y1, y2;
177 const int nr_poly_points =
static_cast<int>(verts.vertices.size ());
178 double xold = cloud[verts.vertices[nr_poly_points - 1]].getVector3fMap ()[PlaneDim1];
179 double yold = cloud[verts.vertices[nr_poly_points - 1]].getVector3fMap ()[PlaneDim2];
180 for (
int i = 0; i < nr_poly_points; i++)
182 const double xnew = cloud[verts.vertices[i]].getVector3fMap ()[PlaneDim1];
183 const double ynew = cloud[verts.vertices[i]].getVector3fMap ()[PlaneDim2];
199 if ((xnew < point.getVector3fMap ()[PlaneDim1]) == (point.getVector3fMap ()[PlaneDim1] <= xold) &&
200 (point.getVector3fMap ()[PlaneDim2] - y1) * (x2 - x1) < (y2 - y1) * (point.getVector3fMap ()[PlaneDim1] - x1))
212 template<
typename Po
intT>
bool
214 const Eigen::Vector3f& ray,
215 const Vertices& verts,
226 assert (verts.vertices.size () == 3);
228 const Eigen::Vector3f p = point.getVector3fMap ();
229 const Eigen::Vector3f a = cloud[verts.vertices[0]].getVector3fMap ();
230 const Eigen::Vector3f b = cloud[verts.vertices[1]].getVector3fMap ();
231 const Eigen::Vector3f c = cloud[verts.vertices[2]].getVector3fMap ();
232 const Eigen::Vector3f u = b - a;
233 const Eigen::Vector3f v = c - a;
234 const Eigen::Vector3f n = u.cross (v);
235 const float n_dot_ray = n.dot (ray);
237 if (std::fabs (n_dot_ray) < 1e-9)
240 const float r = n.dot (a - p) / n_dot_ray;
245 const Eigen::Vector3f w = p + r * ray - a;
246 const float denominator = u.dot (v) * u.dot (v) - u.dot (u) * v.dot (v);
247 const float s_numerator = u.dot (v) * w.dot (v) - v.dot (v) * w.dot (u);
248 const float s = s_numerator / denominator;
252 const float t_numerator = u.dot (v) * w.dot (u) - u.dot (u) * w.dot (v);
253 const float t = t_numerator / denominator;
254 if (t < 0 || s+t > 1)
260 #define PCL_INSTANTIATE_CropHull(T) template class PCL_EXPORTS pcl::CropHull<T>;
Filter points that lie inside or outside a 3D closed surface or 2D closed polygon,...
void applyFilter(Indices &indices) override
Filter the input points using the 2D or 3D polygon hull.
PointCloud represents the base class in PCL for storing collections of 3D points.
IndicesAllocator<> Indices
Type used for indices in PCL.
A point structure representing Euclidean xyz coordinates, and the RGB color.
Describes a set of vertices in a polygon mesh, by basically storing an array of indices.