|
Point Cloud Library (PCL)
1.6.0
|
00001 /* 00002 * Software License Agreement (BSD License) 00003 * 00004 * Point Cloud Library (PCL) - www.pointclouds.org 00005 * Copyright (c) 2009-2012, Willow Garage, Inc. 00006 * 00007 * All rights reserved. 00008 * 00009 * Redistribution and use in source and binary forms, with or without 00010 * modification, are permitted provided that the following conditions 00011 * are met: 00012 * 00013 * * Redistributions of source code must retain the above copyright 00014 * notice, this list of conditions and the following disclaimer. 00015 * * Redistributions in binary form must reproduce the above 00016 * copyright notice, this list of conditions and the following 00017 * disclaimer in the documentation and/or other materials provided 00018 * with the distribution. 00019 * * Neither the name of Willow Garage, Inc. nor the names of its 00020 * contributors may be used to endorse or promote products derived 00021 * from this software without specific prior written permission. 00022 * 00023 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 00024 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 00025 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 00026 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 00027 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 00028 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 00029 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 00030 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 00031 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 00032 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 00033 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 00034 * POSSIBILITY OF SUCH DAMAGE. 00035 * 00036 */ 00037 00038 #ifndef PCL_SAMPLE_CONSENSUS_MODEL_CONE_H_ 00039 #define PCL_SAMPLE_CONSENSUS_MODEL_CONE_H_ 00040 00041 #include <pcl/sample_consensus/sac_model.h> 00042 #include <pcl/sample_consensus/model_types.h> 00043 #include <boost/thread/mutex.hpp> 00044 #include <pcl/common/common.h> 00045 #include <pcl/common/distances.h> 00046 #include <limits.h> 00047 00048 namespace pcl 00049 { 00051 00065 template <typename PointT, typename PointNT> 00066 class SampleConsensusModelCone : public SampleConsensusModel<PointT>, public SampleConsensusModelFromNormals<PointT, PointNT> 00067 { 00068 using SampleConsensusModel<PointT>::input_; 00069 using SampleConsensusModel<PointT>::indices_; 00070 using SampleConsensusModel<PointT>::radius_min_; 00071 using SampleConsensusModel<PointT>::radius_max_; 00072 using SampleConsensusModelFromNormals<PointT, PointNT>::normals_; 00073 using SampleConsensusModelFromNormals<PointT, PointNT>::normal_distance_weight_; 00074 00075 public: 00076 typedef typename SampleConsensusModel<PointT>::PointCloud PointCloud; 00077 typedef typename SampleConsensusModel<PointT>::PointCloudPtr PointCloudPtr; 00078 typedef typename SampleConsensusModel<PointT>::PointCloudConstPtr PointCloudConstPtr; 00079 00080 typedef boost::shared_ptr<SampleConsensusModelCone> Ptr; 00081 00085 SampleConsensusModelCone (const PointCloudConstPtr &cloud) : 00086 SampleConsensusModel<PointT> (cloud), axis_ (Eigen::Vector3f::Zero ()), eps_angle_ (0), min_angle_ (-std::numeric_limits<double>::max()), max_angle_ (std::numeric_limits<double>::max()), 00087 tmp_inliers_ () 00088 { 00089 } 00090 00095 SampleConsensusModelCone (const PointCloudConstPtr &cloud, const std::vector<int> &indices) : 00096 SampleConsensusModel<PointT> (cloud, indices), 00097 axis_ (Eigen::Vector3f::Zero ()), eps_angle_ (0), min_angle_ (-std::numeric_limits<double>::max()), max_angle_ (std::numeric_limits<double>::max()), 00098 tmp_inliers_ () 00099 { 00100 } 00101 00105 SampleConsensusModelCone (const SampleConsensusModelCone &source) : 00106 SampleConsensusModel<PointT> (), axis_ (), eps_angle_ (), min_angle_ (), max_angle_ (), tmp_inliers_ () 00107 { 00108 *this = source; 00109 } 00110 00114 inline SampleConsensusModelCone& 00115 operator = (const SampleConsensusModelCone &source) 00116 { 00117 SampleConsensusModel<PointT>::operator=(source); 00118 axis_ = source.axis_; 00119 eps_angle_ = source.eps_angle_; 00120 min_angle_ = source.min_angle_; 00121 max_angle_ = source.max_angle_; 00122 tmp_inliers_ = source.tmp_inliers_; 00123 return (*this); 00124 } 00125 00129 inline void 00130 setEpsAngle (double ea) { eps_angle_ = ea; } 00131 00133 inline double 00134 getEpsAngle () const { return (eps_angle_); } 00135 00139 inline void 00140 setAxis (const Eigen::Vector3f &ax) { axis_ = ax; } 00141 00143 inline Eigen::Vector3f 00144 getAxis () const { return (axis_); } 00145 00151 inline void 00152 setMinMaxOpeningAngle (const double &min_angle, const double &max_angle) 00153 { 00154 min_angle_ = min_angle; 00155 max_angle_ = max_angle; 00156 } 00157 00162 inline void 00163 getMinMaxOpeningAngle (double &min_angle, double &max_angle) const 00164 { 00165 min_angle = min_angle_; 00166 max_angle = max_angle_; 00167 } 00168 00175 bool 00176 computeModelCoefficients (const std::vector<int> &samples, 00177 Eigen::VectorXf &model_coefficients); 00178 00183 void 00184 getDistancesToModel (const Eigen::VectorXf &model_coefficients, 00185 std::vector<double> &distances); 00186 00192 void 00193 selectWithinDistance (const Eigen::VectorXf &model_coefficients, 00194 const double threshold, 00195 std::vector<int> &inliers); 00196 00203 virtual int 00204 countWithinDistance (const Eigen::VectorXf &model_coefficients, 00205 const double threshold); 00206 00207 00214 void 00215 optimizeModelCoefficients (const std::vector<int> &inliers, 00216 const Eigen::VectorXf &model_coefficients, 00217 Eigen::VectorXf &optimized_coefficients); 00218 00219 00226 void 00227 projectPoints (const std::vector<int> &inliers, 00228 const Eigen::VectorXf &model_coefficients, 00229 PointCloud &projected_points, 00230 bool copy_data_fields = true); 00231 00237 bool 00238 doSamplesVerifyModel (const std::set<int> &indices, 00239 const Eigen::VectorXf &model_coefficients, 00240 const double threshold); 00241 00243 inline pcl::SacModel 00244 getModelType () const { return (SACMODEL_CONE); } 00245 00246 protected: 00251 double 00252 pointToAxisDistance (const Eigen::Vector4f &pt, const Eigen::VectorXf &model_coefficients); 00253 00255 std::string 00256 getName () const { return ("SampleConsensusModelCone"); } 00257 00258 protected: 00262 bool 00263 isModelValid (const Eigen::VectorXf &model_coefficients); 00264 00269 bool 00270 isSampleGood (const std::vector<int> &samples) const; 00271 00272 private: 00274 Eigen::Vector3f axis_; 00275 00277 double eps_angle_; 00278 00280 double min_angle_; 00281 double max_angle_; 00282 00284 const std::vector<int> *tmp_inliers_; 00285 00286 #if defined BUILD_Maintainer && defined __GNUC__ && __GNUC__ == 4 && __GNUC_MINOR__ > 3 00287 #pragma GCC diagnostic ignored "-Weffc++" 00288 #endif 00289 00290 struct OptimizationFunctor : pcl::Functor<float> 00291 { 00297 OptimizationFunctor (int m_data_points, pcl::SampleConsensusModelCone<PointT, PointNT> *model) : 00298 pcl::Functor<float> (m_data_points), model_ (model) {} 00299 00305 int 00306 operator() (const Eigen::VectorXf &x, Eigen::VectorXf &fvec) const 00307 { 00308 Eigen::Vector4f apex (x[0], x[1], x[2], 0); 00309 Eigen::Vector4f axis_dir (x[3], x[4], x[5], 0); 00310 float opening_angle = x[6]; 00311 00312 float apexdotdir = apex.dot (axis_dir); 00313 float dirdotdir = 1.0f / axis_dir.dot (axis_dir); 00314 00315 for (int i = 0; i < values (); ++i) 00316 { 00317 // dist = f - r 00318 Eigen::Vector4f pt (model_->input_->points[(*model_->tmp_inliers_)[i]].x, 00319 model_->input_->points[(*model_->tmp_inliers_)[i]].y, 00320 model_->input_->points[(*model_->tmp_inliers_)[i]].z, 0); 00321 00322 // Calculate the point's projection on the cone axis 00323 float k = (pt.dot (axis_dir) - apexdotdir) * dirdotdir; 00324 Eigen::Vector4f pt_proj = apex + k * axis_dir; 00325 00326 // Calculate the actual radius of the cone at the level of the projected point 00327 Eigen::Vector4f height = apex-pt_proj; 00328 float actual_cone_radius = tanf (opening_angle) * height.norm (); 00329 00330 fvec[i] = static_cast<float> (pcl::sqrPointToLineDistance (pt, apex, axis_dir) - actual_cone_radius * actual_cone_radius); 00331 } 00332 return (0); 00333 } 00334 00335 pcl::SampleConsensusModelCone<PointT, PointNT> *model_; 00336 }; 00337 #if defined BUILD_Maintainer && defined __GNUC__ && __GNUC__ == 4 && __GNUC_MINOR__ > 3 00338 #pragma GCC diagnostic warning "-Weffc++" 00339 #endif 00340 }; 00341 } 00342 00343 #endif //#ifndef PCL_SAMPLE_CONSENSUS_MODEL_CONE_H_
1.7.6.1