利用PCL通过对PLY文件转换为PCD文件,实现PLY文件读取

因实验需要,需要对PLY文件进行读取,因为所使用的PLY文件是利用深度相机获得,所以文件格式与一般的标准的PLY文件稍微有些出入。采用了网上读取的各种方法结果都会有些问题。所以对整个过程进行了总结,来记录一下。


  • 数据文件:

通过数据文件可以发现,本文件中一行是XYZ一行是RGB。
利用PCL通过对PLY文件转换为PCD文件,实现PLY文件读取_第1张图片

  • 使用pcl::io::loadPLYFile()对直接PLY文件进行读取

利用PCL中的函数pcl::io::loadPLYFile()进行文件读取时,会报错:

[pcl::PLYReader] F:\PLY\fakepeople7.ply:12: property ‘list uint8 int32 vertex_indices’ of element ‘face’ is not handled [pcl::PLYReader]
F:\PLY\fakepeople7.ply:14: parse error [pcl::PLYReader]
F:\PLY\fakepeople7.ply:14: parse error: element property count doesn’t match the declaration in the header
[pcl::PLYReader::read] problem
parsing header! [pcl::PLYReader::read] problem parsing header!

尝试修改文件的头部声明,还是无法解决。

  • 利用VTK的IO接口读取文件并进行转化,最终获取PCD

参考链接:https://blog.csdn.net/Charles_ke/article/details/86597223

运行时在函数pcl::io::loadPolygonFilePLY()会报错。

但是同样的代码,换一个PLY文件进行可视化,就有结果:
利用PCL通过对PLY文件转换为PCD文件,实现PLY文件读取_第2张图片
该PLY文件的数据格式如下:
利用PCL通过对PLY文件转换为PCD文件,实现PLY文件读取_第3张图片
考虑到可能是数据格式的问题,所以最后采用最笨的办法,对PLY文件按行读取,来生成最后的PCD文件。

  • 按行读取PLY文件

大概思路:按行读取文件,第3行确定点的个数;然后按行继续读取文件中点云的坐标与颜色信息,并生成最终的点云。

struct point3f {
    float x;
    float y;
    float z;
};
struct rgb3d {
    int r;
    int g;
    int b;
};
PointCloud::Ptr read_ply(char* filename) {  //输入为文件路径
    pcl::PointCloud::Ptr cloud(new pcl::PointCloud);
    ifstream file;
    file.open(filename);
    string temp;
    int i = -1;
    vector xyz;
    vector rgb;
    int num;
    while (getline(file, temp))  //按行读取并赋值给temp
    {
        i++;
        point3f p;
        rgb3d c;
        stringstream ss;
        if (i == 3) {
            num = atoi(temp.substr(15).c_str());  //在本文件中第三行存取了点的个数
        }
        else {
            if (i > 12 && i< num * 2 + 13) {
                if (i % 2 != 0) {
                    ss << temp;
                    ss >> p.x; ss >> p.y; ss >> p.z;
                    xyz.push_back(p);  //点的坐标存储
                }
                else {
                    ss << temp;
                    ss >> c.r; ss >> c.g; ss >> c.b;
                    rgb.push_back(c);  //点的颜色存储
                }
            }
            else {
                continue;
            }
        }
    }
    cloud->width = num;
    cloud->height = 1;
    cloud->is_dense = false;
    cloud->points.resize(cloud->width * cloud->height);
    for (int j = 0; j < xyz.size(); j++) {
        cloud->points[j].x = xyz[j].x;
        cloud->points[j].y = xyz[j].y;
        cloud->points[j].z = xyz[j].z;
        cloud->points[j].r = rgb[j].r;
        cloud->points[j].g = rgb[j].g;
        cloud->points[j].b = rgb[j].b;
    }
    return cloud;
}

最后文件的可视化效果如下:
利用PCL通过对PLY文件转换为PCD文件,实现PLY文件读取_第4张图片

你可能感兴趣的:(c++)