00001 #include <Eigen/Core>
00002 #include <pcl/point_types.h>
00003 #include <pcl/point_cloud.h>
00004 #include <pcl/common/time.h>
00005 #include <pcl/console/print.h>
00006 #include <pcl/features/normal_3d_omp.h>
00007 #include <pcl/features/fpfh_omp.h>
00008 #include <pcl/filters/filter.h>
00009 #include <pcl/filters/voxel_grid.h>
00010 #include <pcl/io/pcd_io.h>
00011 #include <pcl/registration/icp.h>
00012 #include <pcl/registration/sample_consensus_prerejective.h>
00013 #include <pcl/segmentation/sac_segmentation.h>
00014 #include <pcl/visualization/pcl_visualizer.h>
00015
00016
00017 typedef pcl::PointNormal PointNT;
00018 typedef pcl::PointCloud<PointNT> PointCloudT;
00019 typedef pcl::FPFHSignature33 FeatureT;
00020 typedef pcl::FPFHEstimationOMP<PointNT,PointNT,FeatureT> FeatureEstimationT;
00021 typedef pcl::PointCloud<FeatureT> FeatureCloudT;
00022 typedef pcl::visualization::PointCloudColorHandlerCustom<PointNT> ColorHandlerT;
00023
00024
00025 int
00026 main (int argc, char **argv)
00027 {
00028
00029 PointCloudT::Ptr object (new PointCloudT);
00030 PointCloudT::Ptr object_aligned (new PointCloudT);
00031 PointCloudT::Ptr scene (new PointCloudT);
00032 FeatureCloudT::Ptr object_features (new FeatureCloudT);
00033 FeatureCloudT::Ptr scene_features (new FeatureCloudT);
00034
00035
00036 if (argc != 3)
00037 {
00038 pcl::console::print_error ("Syntax is: %s object.pcd scene.pcd\n", argv[0]);
00039 return (1);
00040 }
00041
00042
00043 pcl::console::print_highlight ("Loading point clouds...\n");
00044 if (pcl::io::loadPCDFile<PointNT> (argv[1], *object) < 0 ||
00045 pcl::io::loadPCDFile<PointNT> (argv[2], *scene) < 0)
00046 {
00047 pcl::console::print_error ("Error loading object/scene file!\n");
00048 return (1);
00049 }
00050
00051
00052 pcl::console::print_highlight ("Downsampling...\n");
00053 pcl::VoxelGrid<PointNT> grid;
00054 const float leaf = 0.005f;
00055 grid.setLeafSize (leaf, leaf, leaf);
00056 grid.setInputCloud (object);
00057 grid.filter (*object);
00058 grid.setInputCloud (scene);
00059 grid.filter (*scene);
00060
00061
00062 pcl::console::print_highlight ("Estimating scene normals...\n");
00063 pcl::NormalEstimationOMP<PointNT,PointNT> nest;
00064 nest.setRadiusSearch (0.015);
00065 nest.setInputCloud (scene);
00066 nest.compute (*scene);
00067
00068
00069 pcl::console::print_highlight ("Estimating features...\n");
00070 FeatureEstimationT fest;
00071 fest.setRadiusSearch (0.025);
00072 fest.setInputCloud (object);
00073 fest.setInputNormals (object);
00074 fest.compute (*object_features);
00075 fest.setInputCloud (scene);
00076 fest.setInputNormals (scene);
00077 fest.compute (*scene_features);
00078
00079
00080 pcl::console::print_highlight ("Starting alignment...\n");
00081 pcl::SampleConsensusPrerejective<PointNT,PointNT,FeatureT> align;
00082 align.setInputSource (object);
00083 align.setSourceFeatures (object_features);
00084 align.setInputTarget (scene);
00085 align.setTargetFeatures (scene_features);
00086 align.setNumberOfSamples (3);
00087 align.setCorrespondenceRandomness (2);
00088 align.setSimilarityThreshold (0.6f);
00089 align.setMaxCorrespondenceDistance (1.5f * leaf);
00090 align.setInlierFraction (0.25f);
00091 align.align (*object_aligned);
00092
00093 if (align.hasConverged ())
00094 {
00095
00096 Eigen::Matrix4f transformation = align.getFinalTransformation ();
00097 pcl::console::print_info (" | %6.3f %6.3f %6.3f | \n", transformation (0,0), transformation (0,1), transformation (0,2));
00098 pcl::console::print_info ("R = | %6.3f %6.3f %6.3f | \n", transformation (1,0), transformation (1,1), transformation (1,2));
00099 pcl::console::print_info (" | %6.3f %6.3f %6.3f | \n", transformation (2,0), transformation (2,1), transformation (2,2));
00100 pcl::console::print_info ("\n");
00101 pcl::console::print_info ("t = < %0.3f, %0.3f, %0.3f >\n", transformation (0,3), transformation (1,3), transformation (2,3));
00102 pcl::console::print_info ("\n");
00103 pcl::console::print_info ("Inliers: %i/%i\n", align.getInliers ().size (), object->size ());
00104
00105
00106 pcl::visualization::PCLVisualizer visu("Alignment");
00107 visu.addPointCloud (scene, ColorHandlerT (scene, 0.0, 255.0, 0.0), "scene");
00108 visu.addPointCloud (object_aligned, ColorHandlerT (object_aligned, 0.0, 0.0, 255.0), "object_aligned");
00109 visu.spin ();
00110 }
00111 else
00112 {
00113 pcl::console::print_error ("Alignment failed!\n");
00114 return (1);
00115 }
00116
00117 return (0);
00118 }