点云的处理

一、激光点云

       激光点云指的是由三维激光雷达设备扫描得到的空间点的数据集,每一个点云都包含了三维坐标(XYZ)和激光反射强度(Intensity),其中强度信息会与目标物表面材质与粗糙度、激光入射角度、激光波长以及激光雷达的能量密度有关。

 

上述自定义数据包中的自定义点云(CustomPoint)格式 :

uint32 offset_time      # offset time relative to the base time
float32 x               # X axis, unit:m
float32 y               # Y axis, unit:m
float32 z               # Z axis, unit:m
uint8 reflectivity      # reflectivity, 0~255
uint8 tag               # livox tag
uint8 line              # laser number in lidar

 Livox雷达驱动程序发布点云格式CustomMsg、PointCloud2、pcl::PointXYZI、pcl::PointXYZINormal解析_代码多少钱一两的博客-CSDN博客

二、基于python的点云相加及保存

2.1 两个单独点云

 
# coding:utf-8
import open3d as o3d
import numpy as np
 
# --------------------------- 加载点云 ---------------------------
print("->正在加载点云... ")
pcd1 = o3d.io.read_point_cloud("lidar1.pcd")
pcd2 = o3d.io.read_point_cloud("lidar2.pcd")
 
print("原始点云pcd1:", pcd1)
print("原始点云pcd2:", pcd2)
 
pcd_all = pcd2 + pcd1
print("原始点云pcd_all:", pcd_all)
# ==============================================================
o3d.visualization.draw_geometries([ pcd_all], window_name="wechat 394467238 ")
path_new = '/home/nvidia/LVI_ws/src/r3live_tools/calib/pcds/final_4.pcd'
o3d.io.write_point_cloud(path_new, pcd_all)

2.2 文件夹下所有点云相加

 
# coding:utf-8
import open3d as o3d
import numpy as np
import glob
import os
import shutil
import sys


def find_glob(pathname):
    # type:(str) -> list
    """Find files by glob."""
    files = glob.glob(pathname)
    if len(files) > 0:
        return files
    else:
        print("Error: " + pathname + " is not found")
        exit()
# --------------------------- 加载点云 ---------------------------
print("->正在加载点云... ")
pcd_dir = "/home/nvidia/LVI_ws/src/r3live_tools/calib/pcds/"
pcd_files = find_glob(pcd_dir + "out_*.pcd")
print(len(pcd_files))
pcd_all=o3d.io.read_point_cloud(pcd_files[0])
for i in range(1,len(pcd_files)):
    print(pcd_files[i])
    pcd_dir_single = pcd_files[i]
    pcd= o3d.io.read_point_cloud(pcd_dir_single)
    print("原始点云pcd:", pcd)
    pcd_all=pcd_all+pcd

print("原始点云pcd_all:", pcd_all)
# ==============================================================
o3d.visualization.draw_geometries([ pcd_all], window_name="wechat 394467238 ")
path_new = '/home/nvidia/LVI_ws/src/r3live_tools/calib/pcds/final_5.pcd'
o3d.io.write_point_cloud(path_new, pcd_all)

存在的问题:该点云相加的方法,没有办法完成强度信息的载入,对激光雷达进行相加会丢失轻度信息。

三、基于c++的点云相加

3.1 简单的点云的输出

CMakeLists.txt

cmake_minimum_required(VERSION 2.6)

project(pcl_test)

find_package(PCL REQUIRED)

include_directories(${PCL_INCLUDE_DIRS})

link_directories(${PCL_LIBRARY_DIRS})

add_definitions(${PCL_DEFINITIONS})

add_executable(pcl_test pcl_test.cpp)

target_link_libraries (pcl_test ${PCL_LIBRARIES})

install(TARGETS pcl_test RUNTIME DESTINATION bin)

pcl_test.cpp

#include <iostream>
#include <pcl/io/pcd_io.h>
#include <pcl/point_types.h>

 
int main (int argc, char** argv)
{
  pcl::PointCloud<pcl::PointXYZ> cloud;
 
  // Fill in the cloud data
  cloud.width    = 5;
  cloud.height   = 1;
  cloud.is_dense = false;
  cloud.points.resize (cloud.width * cloud.height);
 
  for (size_t i = 0; i < cloud.points.size (); ++i)
  {
    cloud.points[i].x = 1024 * rand () / (RAND_MAX + 1.0f);
    cloud.points[i].y = 1024 * rand () / (RAND_MAX + 1.0f);
    cloud.points[i].z = 1024 * rand () / (RAND_MAX + 1.0f);
  }
 
  pcl::io::savePCDFileASCII ("test_pcd.pcd", cloud);
  std::cerr << "Saved " << cloud.points.size () << " data points to test_pcd.pcd." << std::endl;
 
  for (size_t i = 0; i < cloud.points.size (); ++i)
    std::cerr << "    " << cloud.points[i].x << " " << cloud.points[i].y << " " << cloud.points[i].z << std::endl;
 
  return (0);
}

2.2 带强度信息的点云的读取和保存

#include <iostream>
#include <pcl/io/pcd_io.h>
#include <pcl/point_types.h>
#include <pcl/visualization/cloud_viewer.h>
#include <iostream>
#include <pcl/io/io.h>
#include <pcl/io/pcd_io.h>//pcd 读写类相关的头文件。
#include <pcl/io/ply_io.h>
#include <pcl/point_types.h>//PCL中支持的点类型头文件。
#include <boost/thread/thread.hpp>


using namespace std; 


void viewerOneOff(pcl::visualization::PCLVisualizer& viewer)
{
    viewer.setBackgroundColor(0.0, 0.5, 0.0);//设置背景颜色
}
int main (int argc, char** argv)
{
  typedef pcl::PointXYZI PointType;
  typedef pcl::PointCloud<PointType> PointCloud;
  std::string filename = "/home/nvidia/LVI_ws/src/r3live_tools/calib/pcds/out_1681117387928485.pcd";
  std::string pcd_file = "/home/nvidia/LVI_ws/src/r3live_tools/calib/pcds/01.pcd";
  PointCloud::Ptr cloud_in(new PointCloud);
  //pcl::PointCloud<pcl::PointXYZ>::Ptr cloud(new pcl::PointCloud<pcl::PointXYZ>);
  if (-1 == pcl::io::loadPCDFile<PointType>(filename, *cloud_in))
  {
      std::cout << "Load pcd file fail!" << std::endl;
      return -1;
  }
  std::cout << cloud_in->points.size() << std::endl;
  pcl::PCDWriter writer;
  writer.write(pcd_file, *cloud_in); 
  std::cout << "从点云数据中读取: " << (*cloud_in).width * (*cloud_in).height <<
        "字节,数据中所包含的有效字段为: " << pcl::getFieldsList(*cloud_in) << std::endl;
  std::cout << (*cloud_in).points.size() << std::endl;
  // pcl::visualization::CloudViewer viewer("First Cloud Viewer");
  // viewer.showCloud(cloud_in);//显示
  // viewer.runOnVisualizationThreadOnce(viewerOneOff);
  // std::cout << "PCL Test OK!\n";
 
}

猜你喜欢

转载自blog.csdn.net/YOULANSHENGMENG/article/details/130082140