A visual function
void viewPort2(pcl::PointCloud<pcl::PointXYZ>::Ptr inputCloud, pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_filtered) {<!-- --> pcl::visualization::PCLVisualizer::Ptr viewer(new pcl::visualization::PCLVisualizer("Comparison before and after filtering")); /*-----Viewport 1-----*/ int v1(0); viewer->createViewPort(0.0, 0.0, 0.5, 1.0, v1); //Set the minimum and maximum values of the first viewport on the X-axis and Y-axis, with values between 0-1 viewer->setBackgroundColor(0, 0, 0, v1); //Set the background color, 0-1, default black (0, 0, 0) viewer->addText("before_filtered", 10, 10, "v1_text", v1); viewer->addPointCloud<pcl::PointXYZ>(inputCloud, "before_filtered_cloud", v1); /*-----Viewport2-----*/ int v2(0); viewer->createViewPort(0.5, 0.0, 1.0, 1.0, v2); viewer->setBackgroundColor(0.3, 0.3, 0.3, v2); viewer->addText("after_filtered", 10, 10, "v2_text", v2); viewer->addPointCloud<pcl::PointXYZ>(cloud_filtered, "after_filtered_cloud", v2); viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_POINT_SIZE, 2, "befor_filtered_cloud", v1); //Set the color of the point cloud to red viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_COLOR, 1, 0, 0, "befor_filtered_cloud", v1); viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_POINT_SIZE, 2, "after_filtered_cloud", v2); viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_COLOR, 0, 1, 0, "after_filtered_cloud", v2); viewer->resetCamera(); viewer->spin(); while (!viewer->wasStopped()) {<!-- --> viewer->spinOnce(); } }
1. pcl::PassThrough filtering
1.1 Required header files
#include <pcl/filters/passthrough.h>
1.2 Code Implementation
Process: Read in point cloud->Create pass-through filter->Set filter field->Execute->Save and visualize
/* * Connect the point cloud coordinate constraints of the X, Y, and Z axes of the point cloud to perform filtering. You can constrain only the Z axis, or the X, Y, and Z coordinate axes can be constrained together to achieve the point cloud filtering effect. * Algorithm principle: Filter a specified dimension and remove points within (or outside) the user-specified field range. */ void pcdPassthrough(pcl::PointCloud<pcl::PointXYZ>::Ptr inputCloud) {<!-- --> pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_filtered_z(new pcl::PointCloud<pcl::PointXYZ>); //Filtered point cloud pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_filtered_y(new pcl::PointCloud<pcl::PointXYZ>); //Filtered point cloud cout << "<-Direct pass filtering in progress->" << endl; pcl::PassThrough<pcl::PointXYZ> pt; // Create a pass filter object pt.setInputCloud(inputCloud); //Set input point cloud pt.setFilterFieldName("z"); //Set the field z required for filtering pt.setFilterLimits(-3, 10); //Set the y field filter range pt.setFilterLimitsNegative(true); //Default false, retain point clouds within the range; true, save point clouds outside the range pt.filter(*cloud_filtered_z); //Perform filtering and save the filtered point cloud pt.setFilterFieldName("y"); //Set the field y required for filtering pt.setFilterLimits(-3, 10); //Set the y field filter range pt.setFilterLimitsNegative(true); //Default false, retain point clouds within the range; true, save point clouds outside the range pt.filter(*cloud_filtered_y); //Perform filtering and save the filtered point cloud ///Save the filtered point cloud cout << "<-Saving point cloud->\\ "; if (cloud_filtered_z->empty() || cloud_filtered_y->empty()) {<!-- --> PCL_ERROR("The saved point cloud is empty!\\ "); return ; } else {<!-- --> pcl::io::savePCDFileBinary("../pcdFile//z_cloud_filtered.pcd", *cloud_filtered_z); cout << "\t\t<field z filtered point cloud information>\\ " << *cloud_filtered_z << endl; pcl::io::savePCDFileBinary("../pcdFile//y_cloud_filtered.pcd", *cloud_filtered_y); cout << "\t\t<field y filtered point cloud information>\\ " << *cloud_filtered_y << endl; } //================================ Comparison visualization before and after filtering============ ====================== pcl::visualization::PCLVisualizer::Ptr viewer(new pcl::visualization::PCLVisualizer("Comparison before and after filtering")); /*-----Viewport 1-----*/ int v1(0); viewer->createViewPort(0.0, 0.0, 0.333, 1.0, v1); //Set the minimum and maximum values of the first viewport on the X-axis and Y-axis, with values between 0-1 viewer->setBackgroundColor(0, 0, 0, v1); //Set the background color, 0-1, default black (0, 0, 0) viewer->addText("before_filtered", 10, 10, "v1_text", v1); viewer->addPointCloud<pcl::PointXYZ>(inputCloud, "before_filtered_cloud", v1); /*-----Viewport2-----*/ int v2(0); viewer->createViewPort(0.3, 0.0, 0.666, 1.0, v2); viewer->setBackgroundColor(0.3, 0.3, 0.3, v2); viewer->addText("z_after_filtered", 10, 10, "v2_text", v2); viewer->addPointCloud<pcl::PointXYZ>(cloud_filtered_z, "z_after_filtered_cloud", v2); /*-----Viewport 3-----*/ int v3(0); viewer->createViewPort(0.666, 0.0, 1.0, 1.0, v3); viewer->setBackgroundColor(0.4, 0.3, 0.5, v3); viewer->addText("y_after_filtered", 10, 10, "v3_text", v3); viewer->addPointCloud<pcl::PointXYZ>(cloud_filtered_y, "y_after_filtered_cloud", v3); /*-----Set related attributes-----*/ //Set the point size of the point cloud to 2 units. This will cause each point in the point cloud to appear as a larger point. viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_POINT_SIZE, 2, "befor_filtered_cloud", v1); //Set the color of the point cloud to red viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_COLOR, 1, 0, 0, "befor_filtered_cloud", v1); viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_POINT_SIZE, 2, "z_after_filtered_cloud", v2); viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_COLOR, 0, 1, 0, "z_after_filtered_cloud", v2); viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_POINT_SIZE, 2, "y_after_filtered_cloud", v3); viewer->setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_COLOR, 0.21, 0.35, 0.15, "y_after_filtered_cloud", v3); viewer->resetCamera(); viewer->spin(); while (!viewer->wasStopped()) {<!-- --> viewer->spinOnce(); } }
1.3 Output results:
2. Voxel filtering pcl::VoxelGrid
2.1 Required header files
#include <pcl/filters/voxel_grid.h>
2.2 Code Implementation
/* *Create a three-dimensional voxel grid -> In each voxel (three-dimensional cube), find the center of gravity of all point clouds in the cube to represent the cube, so as to achieve the purpose of downsampling. */ void pcdVoxelGrid(pcl::PointCloud<pcl::PointXYZ>::Ptr inputCloud) {<!-- --> pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_filtered(new pcl::PointCloud<pcl::PointXYZ>); //Filtered point cloud cout << "<-Voxel downsampling->" << endl; pcl::VoxelGrid<pcl::PointXYZ> vg; //Create filter object vg.setInputCloud(inputCloud); //Set the point cloud to be filtered vg.setLeafSize(0.5f, 0.6f, 0.6f); //Set voxel size vg.filter(*cloud_filtered); //Perform filtering and save the filtering results in cloud_filtered cout << "\t\t<Filtered point cloud information>\\ " << *cloud_filtered << endl; cout << "inputCloud - cloud_filtered = " << inputCloud->width * inputCloud->height - cloud_filtered->width * cloud_filtered->height << endl; viewPort2(inputCloud, cloud_filtered); }
2.3 Output results
3. Uniform Sampling
3.1 Required header files
#include <pcl/keypoints/uniform_sampling.h>
3.2 Code Implementation
/* * Create a filtered sphere for the point cloud data, and then retain a point closest to the center of the voxel at each voxel to replace all points in the voxel. */ void pcdUniformSampling(pcl::PointCloud<pcl::PointXYZ>::Ptr inputCloud) {<!-- --> pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_filtered(new pcl::PointCloud<pcl::PointXYZ>); //Filtered point cloud cout << "<-Uniform downsampling->" << endl; pcl::UniformSampling<pcl::PointXYZ> us; //Create a uniform sampling filter object us.setInputCloud(inputCloud); //Set the point cloud to be filtered us.setRadiusSearch(3.0f); //Set the filter sphere radius us.filter(*cloud_filtered); //Perform filtering and save the filtering results in cloud_filtered cout << "\t\t<Filtered point cloud information>\\ " << *cloud_filtered << endl; cout << "inputCloud - cloud_filtered = " << inputCloud->width * inputCloud->height - cloud_filtered->width * cloud_filtered->height << endl; viewPort2(inputCloud, cloud_filtered); }
3.3 Output results
4. Statistical filtering
4.1 Required header files
#include <pcl/filters/statistical_outlier_removal.h>
4.2 Code Implementation
/* Perform statistical analysis on the neighborhood of each point, and filter out some outlier points that do not meet the requirements based on the distance distribution characteristics from the point to all neighboring points. Disadvantages: The first is that when outliers are clustered in a small range, the algorithm takes more time to ensure the filtering effect; the second is that while filtering outliers, boundary points will be filtered. */ void pcdSOR(pcl::PointCloud<pcl::PointXYZ>::Ptr inputCloud) {<!-- --> pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_filtered(new pcl::PointCloud<pcl::PointXYZ>); //Filtered point cloud cout << "<-statistical filtering->" << endl; pcl::StatisticalOutlierRemoval<pcl::PointXYZ> sor; //Create statistical filter object sor.setInputCloud(inputCloud); //Set the point cloud to be filtered sor.setMeanK(20); //Set the number of neighboring points of the query point sor.setNegative(true);//default false, saves interior points; true, saves filtered outliers sor.setStddevMulThresh(0.1);//Set the standard deviation multiplier to calculate the threshold for outliers sor.filter(*cloud_filtered); //Perform filtering and save the filtering results in cloud_filtered cout << "\t\t<Filtered point cloud information>\\ " << *cloud_filtered << endl; cout << "inputCloud - cloud_filtered = " << inputCloud->width * inputCloud->height - cloud_filtered->width * cloud_filtered->height << endl; viewPort2(inputCloud, cloud_filtered); }
4.3 Output results
Main function
int main() {<!-- --> //Input point cloud source point cloud pcl::PointCloud<pcl::PointXYZ>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZ>); pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_filtered(new pcl::PointCloud<pcl::PointXYZ>); //Filtered point cloud ///Read in point cloud cout << "<-Reading point cloud->" << endl; string cloudPath = "../pcdFile//001.pcd"; if (pcl::io::loadPCDFile(cloudPath, *cloud) < 0) {<!-- --> PCL_ERROR("Point cloud file does not exist!\\ "); system("pause"); return -1; } cout << "\t\t<Read point cloud information>\\ " << *cloud << endl; //pcdVoxelGrid(cloud); pcdSOR(cloud); return 0; }