1 /*
2 * Software License Agreement (BSD License)
3 *
4 *  Copyright (c) 2011, 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 Willow Garage, Inc. 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 *  Author: Anatoly Baskeheev, Itseez Ltd, (myname.mysurname@mycompany.com)
35 */
36 
37 #ifndef _PCL_GPU_FEATURES_HPP_
38 #define _PCL_GPU_FEATURES_HPP_
39 
40 #include <pcl/pcl_macros.h>
41 #include <pcl/point_types.h>
42 #include <pcl/gpu/containers/device_array.h>
43 #include <pcl/gpu/octree/device_format.hpp>
44 #include <pcl/gpu/octree/octree.hpp>
45 
46 namespace pcl
47 {
48     namespace gpu
49     {
50         ////////////////////////////////////////////////////////////////////////////////////////////
51         /** \brief @b Feature represents the base feature class.  */
52 
53         struct PCL_EXPORTS Feature
54         {
55         public:
56             using PointType = PointXYZ;
57             using NormalType = PointXYZ;
58 
59             using PointCloud = DeviceArray<PointType>;
60             using Normals = DeviceArray<NormalType>;
61             using Indices = DeviceArray<int>;
62 
63             Feature();
64 
65             void setInputCloud(const PointCloud& cloud);
66             void setSearchSurface(const PointCloud& surface);
67             void setIndices(const Indices& indices);
68             void setRadiusSearch(float radius, int max_results);
69         protected:
70             PointCloud cloud_;
71             PointCloud surface_;
72             Indices indices_;
73             float radius_;
74             int max_results_;
75 
76             Octree octree_;
77         };
78 
79         ////////////////////////////////////////////////////////////////////////////////////////////
80         /** \brief @b Feature represents the base feature class that takes normals as input also.  */
81 
82         struct PCL_EXPORTS FeatureFromNormals : public Feature
83         {
84         public:
85 
86             void setInputNormals(const Normals& normals);
87         protected:
88             Normals normals_;
89         };
90 
91         ////////////////////////////////////////////////////////////////////////////////////////////
92         /** \brief @b Class for normal estimation.  */
93         class PCL_EXPORTS NormalEstimation : public Feature
94         {
95         public:
96             // float x, y, z, curvature; -> sizeof(PointXYZ) = 4 * sizeof(float)
97             using NormalType = Feature::NormalType;
98 
99             NormalEstimation();
100             void compute(Normals& normals);
101             void setViewPoint(float  vpx, float  vpy, float  vpz);
102             void getViewPoint(float& vpx, float& vpy, float& vpz) const;
103 
104             static void computeNormals(const PointCloud& cloud, const NeighborIndices& nn_indices, Normals& normals);
105             static void flipNormalTowardsViewpoint(const PointCloud& cloud, float vp_x, float vp_y, float vp_z, Normals& normals);
106             static void flipNormalTowardsViewpoint(const PointCloud& cloud, const Indices& indices, float vp_x, float vp_y, float vp_z, Normals& normals);
107         private:
108             float vpx_, vpy_, vpz_;
109             NeighborIndices nn_indices_;
110         };
111 
112         ////////////////////////////////////////////////////////////////////////////////////////////
113         /** \brief @b Class for PFH estimation.  */
114         class PCL_EXPORTS PFHEstimation : public FeatureFromNormals
115         {
116         public:
117             void compute(const PointCloud& cloud, const Normals& normals, const NeighborIndices& neighb_indices, DeviceArray2D<PFHSignature125>& features);
118             void compute(DeviceArray2D<PFHSignature125>& features);
119         private:
120             NeighborIndices nn_indices_;
121             DeviceArray2D<float> data_rpk;
122             int max_elems_rpk;
123         };
124 
125         ////////////////////////////////////////////////////////////////////////////////////////////
126         /** \brief @b Class for PFHRGB estimation.  */
127         class PCL_EXPORTS PFHRGBEstimation : public FeatureFromNormals
128         {
129         public:
130             using PointType = PointXYZ; //16 bytes for xyzrgb
131             void compute(const PointCloud& cloud, const Normals& normals, const NeighborIndices& neighb_indices, DeviceArray2D<PFHRGBSignature250>& features);
132             void compute(DeviceArray2D<PFHRGBSignature250>& features);
133         private:
134             NeighborIndices nn_indices_;
135             DeviceArray2D<float> data_rpk;
136             int max_elems_rpk;
137         };
138 
139         ////////////////////////////////////////////////////////////////////////////////////////////
140         /** \brief @b Class for FPFH estimation.  */
141         class PCL_EXPORTS FPFHEstimation : public FeatureFromNormals
142         {
143         public:
144             FPFHEstimation();
145             virtual ~FPFHEstimation();
146 
147             void compute(DeviceArray2D<FPFHSignature33>& features);
148 
149             void compute(const PointCloud& cloud, const Normals& normals, const NeighborIndices& neighbours, DeviceArray2D<FPFHSignature33>& features);
150 
151         private:
152             NeighborIndices nn_indices_, nn_indices2_;
153 
154             DeviceArray<int> unique_indices_storage;
155             DeviceArray<int> lookup;
156 
157             DeviceArray2D<FPFHSignature33> spfh;
158         };
159 
160         //////////////////////////////////////////////////////////////////////////////////////////////
161         ///** \brief @b Class for PPF estimation.  */
162         class PCL_EXPORTS PPFEstimation : public FeatureFromNormals
163         {
164         public:
165             void compute(DeviceArray<PPFSignature>& features);
166         };
167 
168         //////////////////////////////////////////////////////////////////////////////////////////////
169         ///** \brief @b Class for PPFRGB estimation.  */
170 
171         class PCL_EXPORTS PPFRGBEstimation : public FeatureFromNormals
172         {
173         public:
174 
175             using PointType = PointXYZ; //16 bytes for xyzrgb
176             void compute(DeviceArray<PPFRGBSignature>& features);
177         };
178 
179         //////////////////////////////////////////////////////////////////////////////////////////////
180         ///** \brief @b Class for PPFRGBRegion estimation.  */
181 
182         class PCL_EXPORTS PPFRGBRegionEstimation : public FeatureFromNormals
183         {
184         public:
185             using PointType = PointXYZ; //16 bytes for xyzrgb
186             void compute(DeviceArray<PPFRGBSignature>& features);
187 
188         private:
189             NeighborIndices nn_indices_;
190         };
191 
192 
193         //////////////////////////////////////////////////////////////////////////////////////////////
194         ///** \brief @b Class for PPFRGBRegion estimation.  */
195 
196         class PCL_EXPORTS PrincipalCurvaturesEstimation : public FeatureFromNormals
197         {
198         public:
199 
200             void compute(DeviceArray<PrincipalCurvatures>& features);
201         private:
202             NeighborIndices nn_indices_;
203             DeviceArray2D<float> proj_normals_buf;
204         };
205 
206 
207         //////////////////////////////////////////////////////////////////////////////////////////////
208         ///** \brief @b Class for Viewpoint Feature Histogramm estimation.  */
209 
210         class PCL_EXPORTS VFHEstimation : public FeatureFromNormals
211         {
212         public:
213 
214             enum
215             {
216                 BINS1_F1 = 45,
217                 BINT2_F2 = 45,
218                 BINS3_F3 = 45,
219                 BINS4_F4 = 45,
220                 BINS_VP = 128
221             };
222 
223             VFHEstimation();
224 
225             void setViewPoint(float  vpx, float  vpy, float  vpz);
226             void getViewPoint(float& vpx, float& vpy, float& vpz) const;
227 
228             void setUseGivenNormal (bool use);
229             void setNormalToUse (const NormalType& normal);
230             void setUseGivenCentroid (bool use);
231             void setCentroidToUse (const PointType& centroid);
232 
233             void setNormalizeBins (bool normalize);
234             void setNormalizeDistance (bool normalize);
235             void setFillSizeComponent (bool fill_size);
236 
237             void compute(DeviceArray<VFHSignature308>& feature);
238         private:
239 
240             float vpx_, vpy_, vpz_;
241 
242             bool use_given_normal_;
243             bool use_given_centroid_;
244             bool normalize_bins_;
245             bool normalize_distances_;
246             bool size_component_;
247 
248             NormalType normal_to_use_;
249             PointType centroid_to_use_;
250         };
251 
252 
253         //////////////////////////////////////////////////////////////////////////////////////////////
254         ///** \brief @b Class for SpinImages estimation.  */
255 
256         class PCL_EXPORTS SpinImageEstimation : public FeatureFromNormals
257         {
258         public:
259             using SpinImage = Histogram<153>;
260 
261             SpinImageEstimation (unsigned int image_width = 8,
262                 double support_angle_cos = 0.0,   // when 0, this is bogus, so not applied
263                 unsigned int min_pts_neighb = 0);
264 
265             void setImageWidth (unsigned int bin_count);
266             void setSupportAngle (float support_angle_cos);
267             void setMinPointCountInNeighbourhood (unsigned int min_pts_neighb);
268             void setInputWithNormals (const PointCloud& input, const Normals& normals);
269             void setSearchSurfaceWithNormals (const PointCloud& surface, const Normals& normals);
270 
271             void setRotationAxis (const NormalType& axis);
272             void setInputRotationAxes (const Normals& axes);
273             void useNormalsAsRotationAxis();
274             void setAngularDomain (bool is_angular = true);
275             void setRadialStructure (bool is_radial = true);
276 
277             void compute(DeviceArray2D<SpinImage>& features, DeviceArray<unsigned char>& mask);
278 
279         private:
280             Normals input_normals_;
281             Normals rotation_axes_cloud_;
282 
283             bool is_angular_;
284 
285             NormalType rotation_axis_;
286             bool use_custom_axis_;
287 
288 			/* use input normals as rotation axes*/
289             bool use_custom_axes_cloud_;
290 
291             bool is_radial_;
292 
293             unsigned int image_width_;
294             float support_angle_cos_;
295             unsigned int min_pts_neighb_;
296 
297             bool fake_surface_;
298 
299 			NeighborIndices nn_indices_;
300         };
301     }
302 };
303 
304 #endif /* _PCL_GPU_FEATURES_HPP_ */
305 
306 
307