Example #1
0
//
// 計算 pointcloud 的 VFH, 存成 vfh.pcd
//
void vfh_demo()
{
	string filename;
	cout << "Input filename: ";
	cin >> filename;

	// Create new point clouds to hold data
	pcl::PointCloud<PointType>::Ptr points (new pcl::PointCloud<PointType>);
	pcl::PointCloud<pcl::Normal>::Ptr normals (new pcl::PointCloud<pcl::Normal>);
	pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs(new pcl::PointCloud<pcl::VFHSignature308>);

	// Load point data
	pcl::io::loadPCDFile(filename, *points);

	// Compute normals
	compute_surface_normals(points, normals);

	// Create VFHEstimation
	pcl::VFHEstimation<PointType, pcl::Normal, pcl::VFHSignature308> vfh;
	vfh.setInputCloud(points);
	vfh.setInputNormals(normals);

	pcl::search::KdTree<PointType>::Ptr tree (new pcl::search::KdTree<PointType>());
	vfh.setSearchMethod(tree);
	vfh.compute(*vfhs);

	// Save VFH
	pcl::io::savePCDFileASCII("vfh.pcd", *vfhs);
}
Example #2
0
void mpcl_extract_VFH(pcl::PointCloud<pcl::PointXYZ>::Ptr cloud)
{
    // http://virtuemarket-lab.blogspot.jp/2015/03/viewpoint-feature-histogram.html
    // pcl::PointCloud<pcl::VFHSignature308>::Ptr Extract_VFH(pcl::PointCloud<pcl::PointXYZ>::Ptr cloud)
    pcl::PointCloud<pcl::Normal>::Ptr cloud_normals (new pcl::PointCloud<pcl::Normal> ());
    pcl::VFHEstimation<pcl::PointXYZ, pcl::Normal, pcl::VFHSignature308> vfh;
    pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs (new pcl::PointCloud<pcl::VFHSignature308> ());

    // cloud_normals = surface_normals(cloud);

    vfh.setInputCloud (cloud);
    vfh.setInputNormals (cloud_normals);

    pcl::search::KdTree<pcl::PointXYZ>::Ptr tree (new pcl::search::KdTree<pcl::PointXYZ> ());
    vfh.setSearchMethod (tree);

    vfh.compute (*vfhs);
    // return vfhs;
}
std::vector<float> compute_VFHS_features( pcl::PointCloud<pcl::PointXYZ>::Ptr cloud,pcl::PointCloud<pcl::Normal>::Ptr normals ){

  pcl::VFHEstimation<pcl::PointXYZ, pcl::Normal, pcl::VFHSignature308> vfh;
  vfh.setInputCloud (cloud);
  vfh.setInputNormals (normals);

  pcl::search::KdTree<pcl::PointXYZ>::Ptr tree (new pcl::search::KdTree<pcl::PointXYZ> ());
  vfh.setSearchMethod (tree);

  pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs (new pcl::PointCloud<pcl::VFHSignature308> ());

  vfh.compute (*vfhs);
  pcl::VFHSignature308 value=vfhs->points[0];
  std::cout << value;
  std::vector<float> histogram;
  for(int i=0;i< value.descriptorSize();i++){
    histogram.push_back(value.histogram[i]);
  }
  return histogram;
}
Example #4
0
/** \brief Loads an n-D histogram file as a VFH signature
  * \param path the input file name
  * \param vfh the resultant VFH model
  */
bool
loadHist (const boost::filesystem::path &path, vfh_model &vfh)
{

    pcl::PointCloud<PointType>::Ptr cloud (new pcl::PointCloud<PointType>);
    pcl::PointCloud<NormalType>::Ptr cloud_normals (new pcl::PointCloud<NormalType> ());

    if (pcl::io::loadPCDFile<PointType> (path.string(), *cloud) == -1) {
        PCL_ERROR ("Couldn't read file %s.pcd \n", path.string().c_str());
        return false;
    }
    pcl::PointCloud<PointType>::Ptr cloud_filtered (new pcl::PointCloud<PointType>);
    std::vector<int> filter_index;
    pcl::removeNaNFromPointCloud (*cloud, *cloud_filtered, filter_index);
    cloud = cloud_filtered;

    pcl::NormalEstimationOMP<PointType, NormalType> norm_est;
    norm_est.setKSearch (10);
    norm_est.setInputCloud (cloud);
    norm_est.compute (*cloud_normals);

    pcl::VFHEstimation<PointType, NormalType, pcl::VFHSignature308> vfh_est;
    vfh_est.setInputCloud (cloud);
    vfh_est.setInputNormals (cloud_normals);

    pcl::search::KdTree<PointType>::Ptr tree (new pcl::search::KdTree<PointType> ());
    vfh_est.setSearchMethod (tree);
    pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs (new pcl::PointCloud<pcl::VFHSignature308> ());
    vfh_est.compute (*vfhs);

    vfh.second.resize (308);

    for (size_t i = 0; i < pcl::VFHSignature308::descriptorSize(); ++i)
    {
        vfh.second[i] = vfhs->points[0].histogram[i];
    }
    vfh.first = path.string ();
    return (true);
}
Example #5
0
//Function that recursively reads all files and computes the VFH for them
void VFH::readFilesAndComputeVFH (const boost::filesystem::path &base_dir)
{
	pcl::PointCloud<PointT>::Ptr cloud (new pcl::PointCloud<PointT>);
	pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs(new pcl::PointCloud<pcl::VFHSignature308> ());
	//Recursively read all files and compute VFH
	for(boost::filesystem::directory_iterator it (base_dir); it!=boost::filesystem::directory_iterator (); ++it)
	{
		std::stringstream ss;
		ss << it->path();
		//if its a directory just call back the function
		if (boost::filesystem::is_directory (it->status()))
		{
			pcl::console::print_highlight ("Entering directory %s.\n", ss.str().c_str());
			//call rescursively our function
			readFilesAndComputeVFH(it->path());
		}
		//if not, go ahead and read and process the file
        if (boost::filesystem::is_regular_file (it->status()) && boost::filesystem::extension (it->path()) == VFH_FILES_EXTENSION )
		{
			if(pcl::io::loadPCDFile<PointT> (it->path().string(), *cloud) == -1)
				PCL_ERROR ("Couldn't read the file %s.", it->path().string().c_str());
			else
			{
				pcl::console::print_highlight ("Computing VFH for %s.\n", boost::filesystem::path(*it).string().c_str());
				
				//Finally compute the vfh and save it
				computeVFHistogram(cloud, vfhs);
				
				//save them to file
				pcl::PCDWriter writer;
				std::stringstream ss;
				ss <<boost::filesystem::path(*it).branch_path()<< "/" << boost::filesystem::basename(*it) << ".vfh";
				pcl::console::print_highlight ("writing %s\n", ss.str().c_str());
				writer.write<pcl::VFHSignature308> (ss.str(), *vfhs, false);
			}
		}
	}
}
Example #6
0
void VFH::doTheGuess(const pcl::PointCloud<PointT>::Ptr object, std::vector<std::string> &guesses)
{
	pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs(new pcl::PointCloud<pcl::VFHSignature308> ());
	computeVFHistogram(object, vfhs);
	vfh_model histogram;
	
	pcl::PointCloud <pcl::VFHSignature308> point;

	histogram.second.resize (308);

	std::vector <pcl::PCLPointField> fields;
	int vfh_idx = pcl::getFieldIndex (*vfhs, "vfh", fields);

	for (size_t i = 0; i < fields[vfh_idx].count; ++i)
	{
		histogram.second[i] = vfhs->points[0].histogram[i];
		std::cout<<histogram.second[i]<<std::endl;
	}
	histogram.first = "cloud_from_object.vfh";
	
	//let look for the match
	flann::Index<flann::ChiSquareDistance<float> > index (data, flann::SavedIndexParams ("kdtree.idx"));
	
	index.buildIndex ();
	nearestKSearch (index, histogram, 16, k_indices, k_distances);
	
	pcl::console::print_highlight ("The closest 16 neighbors are:\n");
	for (int i = 0; i < 16; ++i)
	{
		Eigen::Vector4f centroid;
		pcl::compute3DCentroid (*object, centroid);
		std::cerr<<centroid[0]<<centroid[1]<<centroid[2]<<centroid[3]<<std::endl;
		pcl::console::print_info ("    %d - %s (%d) with a distance of: %f\n", 
				i, models.at (k_indices[0][i]).first.c_str (), k_indices[0][i], k_distances[0][i]);
		guesses.push_back(models.at (k_indices[0][i]).first);
	}
}
bool cloud_cb(data_collection::process_cloud::Request &req,
	      data_collection::process_cloud::Response &res)
{
  //Segment from cloud:
  //May need to tweak segmentation parameters to get just the cluster I'm looking for.
  std::vector<pcl::PointCloud<pcl::PointXYZ>::Ptr> clouds;
  nrg_object_recognition::segmentation seg_srv;

  seg_srv.request.scene = req.in_cloud;
  seg_srv.request.min_x = -.75, seg_srv.request.max_x = .4;
  seg_srv.request.min_y = -5, seg_srv.request.max_y = .5;
  seg_srv.request.min_z = 0.0, seg_srv.request.max_z = 1.15;
  seg_client.call(seg_srv);
  
  //SegmentCloud(req.in_cloud, clouds);
  
  //For parameter tweaking, may be good to write all cluseters to file here for examination in pcd viewer.
  
  pcl::PointCloud<pcl::PointXYZ>::Ptr cluster (new pcl::PointCloud<pcl::PointXYZ>);
  //cluster = clouds.at(0);
  pcl::fromROSMsg(seg_srv.response.clusters.at(0), *cluster);
  //std::cout << "found " << clouds.size() << " clusters.\n"; 
  std::cout << "cluster has " << cluster->height*cluster->width << " points.\n";
  
  //Write raw pcd file (objecName_angle.pcd)
  std::stringstream fileName_ss;
  fileName_ss << "data/" << req.objectName << "_" << req.angle << ".pcd";
  std::cout << "writing raw cloud to file...\n";
  std::cout << fileName_ss.str() << std::endl;
  pcl::io::savePCDFile(fileName_ss.str(), *cluster);
  std::cout << "done.\n";
 
  //Write vfh feature to file: 
  pcl::VFHEstimation<pcl::PointXYZ, pcl::Normal, pcl::VFHSignature308> vfh;
  vfh.setInputCloud (cluster);
  //Estimate normals:
  pcl::NormalEstimation<pcl::PointXYZ, pcl::Normal> ne;
  ne.setInputCloud (cluster);
  pcl::search::KdTree<pcl::PointXYZ>::Ptr tree (new pcl::search::KdTree<pcl::PointXYZ> ());
  ne.setSearchMethod (tree);
  pcl::PointCloud<pcl::Normal>::Ptr cloud_normals (new pcl::PointCloud<pcl::Normal>);
  ne.setRadiusSearch (0.03);
  ne.compute (*cloud_normals);
  vfh.setInputNormals (cloud_normals);
  //Estimate vfh:
  vfh.setSearchMethod (tree);
  pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs (new pcl::PointCloud<pcl::VFHSignature308> ());
  // Compute the feature
  vfh.compute (*vfhs);
  //Write to file: (objectName_angle_vfh.pcd)
  fileName_ss.str("");
  std::cout << "writing vfh descriptor to file...\n";
  fileName_ss << "data/" << req.objectName << "_" << req.angle << "_vfh.pcd";
  pcl::io::savePCDFile(fileName_ss.str(), *vfhs);
  std::cout << "done.\n";

 
  //Extract cph
  std::vector<float> feature;
  CPHEstimation cph(5,72);
  cph.setInputCloud(cluster);
  cph.compute(feature);
  //Write cph to file. (objectName_angle.csv)
  std::ofstream outFile;
  fileName_ss.str("");
  fileName_ss << "data/" << req.objectName << "_" << req.angle << ".csv";
  outFile.open(fileName_ss.str().c_str());
  std::cout << "writing cph descriptor to file...\n";
  for(unsigned int j=0; j<feature.size(); j++){
	outFile << feature.at(j) << " "; 
  }
  outFile.close();
  fileName_ss.str("");
  std::cout << "done.\n";
  res.result = 1;
}
Example #8
0
/** \brief Returns closest poses of of objects in training data to the query object
    \param -q the path to the input point cloud
    \param -k the number of nearest neighbors to return
*/
int main (int argc, char **argv)
{
    //parse data directory
    std::string queryCloudName;
    pcl::console::parse_argument (argc, argv, "-q", queryCloudName);
    boost::filesystem::path queryCloudPath(queryCloudName);

    //parse number of nearest neighbors k
    int k = 1;
    pcl::console::parse_argument (argc, argv, "-k", k);
    pcl::console::print_highlight ("using %d nearest neighbors.\n", k); 

    //read in point cloud
    PointCloud::Ptr cloud (new PointCloud);
    pcl::PCDReader reader;
    //read ply file
    pcl::PolygonMesh triangles;
    if(queryCloudPath.extension().native().compare(".ply") == 0)
    {
        if( pcl::io::loadPolygonFilePLY(queryCloudPath.native(), triangles) == -1)
        {
            PCL_ERROR("Could not read .ply file\n");
            return -1;
        }
#if PCL17
        pcl::fromPCLPointCloud2(triangles.cloud, *cloud);
#endif
#if PCL16
        pcl::fromROSMsg(triangles.cloud, *cloud);
#endif
    }
    //read pcd file
    else if(queryCloudPath.extension().native().compare(".pcd") == 0)
    {
        if( reader.read(queryCloudPath.native(), *cloud) == -1)
        {
            PCL_ERROR("Could not read .pcd file\n");
            return -1;
        }
    }
    else
    {
        
        PCL_ERROR("File must have extension .ply or .pcd\n");
        return -1;
    }

    //Move point cloud so it is is centered at the origin
    Eigen::Matrix<float,4,1> centroid;
    pcl::compute3DCentroid(*cloud, centroid);
    pcl::demeanPointCloud(*cloud, centroid, *cloud);

    //Estimate normals
    Normals::Ptr normals (new Normals);
    pcl::NormalEstimation<pcl::PointXYZ, pcl::Normal> normEst;
    normEst.setInputCloud(cloud);
    pcl::search::KdTree<pcl::PointXYZ>::Ptr normTree (new pcl::search::KdTree<pcl::PointXYZ>);
    normEst.setSearchMethod(normTree);
    normEst.setRadiusSearch(0.005);
    normEst.compute(*normals);

    //Create VFH estimation class
    pcl::VFHEstimation<pcl::PointXYZ, pcl::Normal, pcl::VFHSignature308> vfh;
    vfh.setInputCloud(cloud);
    vfh.setInputNormals(normals);
    pcl::search::KdTree<pcl::PointXYZ>::Ptr vfhsTree (new pcl::search::KdTree<pcl::PointXYZ>);
    vfh.setSearchMethod(vfhsTree);

    //calculate VFHS features
    pcl::PointCloud<pcl::VFHSignature308>::Ptr vfhs (new pcl::PointCloud<pcl::VFHSignature308>);
    vfh.setViewPoint(1, 0, 0);
    vfh.compute(*vfhs);
    
    //filenames
    std::string featuresFileName = "training_features.h5";
    std::string anglesFileName = "training_angles.list";
    std::string kdtreeIdxFileName = "training_kdtree.idx";

    //allocate flann matrices
    std::vector<CloudInfo> cloudInfoList;
    std::vector<PointCloud::Ptr> cloudList;
    cloudList.resize(k);
    flann::Matrix<int> k_indices;
    flann::Matrix<float> k_distances;
    flann::Matrix<float> data;

    //load training data angles list
    loadAngleData(cloudInfoList, anglesFileName);
    flann::load_from_file (data, featuresFileName, "training_data");
    flann::Index<flann::ChiSquareDistance<float> > index (data, flann::SavedIndexParams ("training_kdtree.idx"));

    //perform knn search
    index.buildIndex ();
    nearestKSearch (index, vfhs, k, k_indices, k_distances);

    // Output the results on screen
    pcl::console::print_highlight ("The closest %d neighbors are:\n", k);
    for (int i = 0; i < k; ++i)
    {
        //print nearest neighbor info to screen
        pcl::console::print_info ("    %d - theta = %f, phi = %f  (%s) with a distance of: %f\n", 
            i, 
            cloudInfoList.at(k_indices[0][i]).theta*180.0/M_PI, 
            cloudInfoList.at(k_indices[0][i]).phi*180.0/M_PI, 
            cloudInfoList.at(k_indices[0][i]).filePath.c_str(), 
            k_distances[0][i]);

        //retrieve pointcloud and store in list
        PointCloud::Ptr cloudMatch (new PointCloud);
        reader.read(cloudInfoList.at(k_indices[0][i]).filePath.native(), *cloudMatch);

        //Move point cloud so it is is centered at the origin
        pcl::compute3DCentroid(*cloudMatch, centroid);
        pcl::demeanPointCloud(*cloudMatch, centroid, *cloudMatch);

        cloudList[i] = cloudMatch;
    }

    //visualize histogram
    /*
    pcl::visualization::PCLHistogramVisualizer histvis;
    histvis.addFeatureHistogram<pcl::VFHSignature308> (*vfhs, histLength);
    */

    //Visualize point cloud and matches
    //viewpoint cals
    int y_s = (int)std::floor (sqrt ((double)k));
    int x_s = y_s + (int)std::ceil ((k / (double)y_s) - y_s);
    double x_step = (double)(1 / (double)x_s);
    double y_step = (double)(1 / (double)y_s);
    int viewport = 0, l = 0, m = 0;
    std::string viewName = "match number ";

    //setup visualizer and add query cloud 
    pcl::visualization::PCLVisualizer visu("KNN search");
    visu.createViewPort (l * x_step, m * y_step, (l + 1) * x_step, (m + 1) * y_step, viewport);
    visu.addPointCloud<pcl::PointXYZ> (cloud, ColorHandler(cloud, 0.0 , 255.0, 0.0), "Query Cloud Cloud", viewport);
    visu.addText ("Query Cloud", 20, 30, 136.0/255.0, 58.0/255.0, 1, "Query Cloud", viewport); 
    visu.setShapeRenderingProperties (pcl::visualization::PCL_VISUALIZER_FONT_SIZE, 18, "Query Cloud", viewport);
    visu.addCoordinateSystem (0.05, 0);

    //add matches to plot
    for(int i = 1; i < (k+1); ++i)
    {
        //shift viewpoint
        ++l;
        if (l >= x_s)
        {
          l = 0;
          m++;
        }

        //names and text labels
        std::string textString = viewName;
        std::string cloudname = viewName;
        textString.append(boost::lexical_cast<std::string>(i));
        cloudname.append(boost::lexical_cast<std::string>(i)).append("cloud");

        //color proportional to distance

        //add cloud
        visu.createViewPort (l * x_step, m * y_step, (l + 1) * x_step, (m + 1) * y_step, viewport);
        visu.addPointCloud<pcl::PointXYZ> (cloudList[i-1], ColorHandler(cloudList[i-1], 0.0 , 255.0, 0.0), cloudname, viewport);
        visu.addText (textString, 20, 30, 136.0/255.0, 58.0/255.0, 1, textString, viewport);
        visu.setShapeRenderingProperties (pcl::visualization::PCL_VISUALIZER_FONT_SIZE, 18, textString, viewport);
    }
    visu.spin();

    return 0;
}