点云库PCL学习5——点云转深度图

一、定义

通过相机拍摄得到的点云是将深度图经过坐标转换成点云数据。深度图像上的每个像素点的值表达是场景物体离相机的距离。那么如果已知点云,如何转成深度图像呢!

二、使用的函数

头文件:    #include <pcl/visualization/range_image_visualizer.h>

函数:range_image.createFromPointCloud(......)

RangeImage::createFromPointCloud (const PointCloudType& point_cloud, float angular_resolution,
                                  float max_angle_width, float max_angle_height,
                                  const Eigen::Affine3f& sensor_pose, RangeImage::CoordinateFrame coordinate_frame,
                                  float noise_level, float min_range, int border_size)

三、代码

#define  _CRT_SECURE_NO_WARNINGS
#pragma warning(disable:4996)

#include <pcl/range_image/range_image.h>
#include <pcl/visualization/range_image_visualizer.h>
#include <pcl/visualization/pcl_visualizer.h>
#include <pcl/console/parse.h>

void
setViewerPose(pcl::visualization::PCLVisualizer& viewer, const Eigen::Affine3f& viewer_pose)
{
	Eigen::Vector3f pos_vector = viewer_pose * Eigen::Vector3f(0, 0, 0);
	Eigen::Vector3f look_at_vector = viewer_pose.rotation() * Eigen::Vector3f(0, 0, 1) + pos_vector;
	Eigen::Vector3f up_vector = viewer_pose.rotation() * Eigen::Vector3f(0, -1, 0);
	viewer.setCameraPosition(
		pos_vector[0],
		pos_vector[1],
		pos_vector[2],
		look_at_vector[0],
		look_at_vector[1],
		look_at_vector[2],
		up_vector[0],
		up_vector[1],
		up_vector[2]);
}

int
main(int argc, char** argv) {
	pcl::PointCloud<pcl::PointXYZ> pointCloud;
	//生成数据
	for (float y = -0.5f; y <= 0.5f; y += 0.01f)
	{
		for (float z = -0.5f; z <= 0.5f; z += 0.01f)
		{
			pcl::PointXYZ point;
			point.x = 2.0f - y;
			point.y = y;
			point.z = z;
			pointCloud.points.push_back(point);
		}
	}
	pointCloud.width = (uint32_t)pointCloud.points.size();
	pointCloud.height = 1;
	/*以1度为角分辨率,从上面创建的点云创建深度图像。*/
	float angularResolution = (float)(1.0f * (M_PI / 180.0f));  // 1度转弧度
	/*模拟深度传感器在水平方向的最大采样角度:360°视角。*/
	float maxAngleWidth = (float)(360.0f * (M_PI / 180.0f));  // 360.0度转弧度
	/*模拟深度传感器在垂直方向的最大采样角度:180°视角。*/
	float maxAngleHeight = (float)(180.0f * (M_PI / 180.0f)); // 180.0度转弧度
	/*
	sensorPose定义模拟深度传感器的自由度位置:
	横滚角roll、俯仰角pitch、偏航角yaw,默认初始值均为0。
	*/
	Eigen::Affine3f sensorPose = (Eigen::Affine3f)Eigen::Translation3f(0.0f, 0.0f, 0.0f);
	/*
	定义坐标轴正方向:
	CAMERA_FRAME:X轴向右,Y轴向下,Z轴向前;
	LASER_FRAME:X轴向前,Y轴向左,Z轴向上;
	*/
	pcl::RangeImage::CoordinateFrame coordinate_frame = pcl::RangeImage::CAMERA_FRAME;
	/*
	noiseLevel设置周围点对当前点深度值的影响:
	如 noiseLevel=0.05,可以理解为,深度距离值是通过查询点半径为 Scm 的圆内包含的点用来平均计算而得到的。
	*/
	float noiseLevel = 0.00;
	/*
	min_range设置最小的获取距离,小于最小获取距离的位置为盲区
	*/
	float minRange = 0.0f;
	/*border_size获得深度图像的边缘的宽度:在裁剪图像时,如果 borderSize>O ,将在图像周围留下当前视点不可见点的边界*/
	int borderSize = 1;

	boost::shared_ptr<pcl::RangeImage> range_image_ptr(new pcl::RangeImage);
	pcl::RangeImage& range_image = *range_image_ptr;
	range_image.createFromPointCloud(pointCloud, angularResolution, maxAngleWidth, maxAngleHeight, sensorPose, coordinate_frame, noiseLevel, minRange, borderSize);
	std::cout << range_image << "\n";

	//创建3D视图并且添加点云进行显示
	pcl::visualization::PCLVisualizer viewer("3D Viewer");
	viewer.setBackgroundColor(1, 1, 1);
	pcl::visualization::PointCloudColorHandlerCustom<pcl::PointWithRange> range_image_color_handler(range_image_ptr, 0, 0, 0);
	viewer.addPointCloud(range_image_ptr, range_image_color_handler, "range image");
	viewer.setPointCloudRenderingProperties(pcl::visualization::PCL_VISUALIZER_POINT_SIZE, 1, "range image");

	viewer.initCameraParameters();
	setViewerPose(viewer, range_image.getTransformationToWorldSystem());

	//显示深度图像
	pcl::visualization::RangeImageVisualizer range_image_widget("Range image");
	//range_image_widget.setRangeImage(range_image);           
	range_image_widget.showRangeImage(range_image); //图像可视化方式显示深度图像
	Eigen::Affine3f scene_sensor_pose(Eigen::Affine3f::Identity());
	//主循环
	while (!viewer.wasStopped())
	{
		range_image_widget.spinOnce();
		viewer.spinOnce();
		//pcl_Sleep(0.01);
		if (1)
		{
			scene_sensor_pose = viewer.getViewerPose();
			range_image.createFromPointCloud(pointCloud,
				angularResolution, pcl::deg2rad(360.0f),
				pcl::deg2rad(180.0f),
				scene_sensor_pose,
				pcl::RangeImage::LASER_FRAME,
				noiseLevel,
				minRange,
				borderSize);
			range_image_widget.showRangeImage(range_image);
		}
	}

}

四、效果

不明白:为什么深度图会产生成对称形式的啦。。。。。。。。

五、解释

angularResolution 表示相邻像素之间的角差是一度。

maxAngleWidth=360 maxAngleHeight=180表示我们模拟的距离传感器对周围环境是一个完整的360度视图。 通过调整这个值设置激光器扫描的视角,从而减少计算量。 比如:一个激光只需要描述前方的180度的数据,后面的数据可以忽视,那么设置 maxAngleWidth=180 就足够了。

传感器姿态,包含6DoF (6个自由度), 其中roll=pitch=yaw=0.

coordinate_frame=CAMERA_FRAME 表示x面向右,y向下,z轴向前。另一种选择是LASER_FRAME, x面向前,y向左,z向向上。

noiseLevel=0 表示 深度图使用一个归一化的z缓冲区创建的。如果想让邻近点都落在同一个像素单元,用户可以使用较高的值。例如noiseLevel=0.05,深度距离值是通过查询点半径为5cm的圆内包含的点,平均计算而得到的。

如果minRange是大于0的,那么所有深度值小于这个值的点都将被忽略。

自由度总共有6个,可分成两种不同的类型:平移和旋转。

1. 平移运动 刚体可以在3个自由度中平移:向前/向后,向上/向下,向左/向右。

2. 旋转运动 刚体也可以在3个自由度中旋转:纵摇(Pitch)、横摇(Roll)和垂摇(Yaw)。

 

参考链接:https://www.cnblogs.com/sweetdark/p/9025032.html

https://blog.csdn.net/zfjBIT/article/details/92797291

 

  • 2
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
PCL学习教程是关于点云库(Point Cloud Library)的教程,该库可以用于处理和分析来自传感器的三维点云数据。学习PCL的教程通常包括以下内容: 1. 安装PCL:首先,你需要安装PCL库及其依赖项。具体的安装方法可以参考PCL官方网站上的文档。 2. 点云数据的读取和可视化:学习如何读取和可视化点云数据是PCL学习的第一步。使用PCL提供的函数和类,你可以读取来自传感器的点云数据,并将其可视化以便观察和分析。 3. 点云滤波:PCL提供了各种滤波器,用于去除点云中的噪声、采样和下采样,以及提取感兴趣的特征。 4. 特征提取:学习如何从点云中提取表面特征,例如平面、曲率、法线等。 5. 点云配准:点云配准是将多个点云对齐到一个共同的坐标系中的过程。PCL提供了各种配准算法,包括ICP(迭代最近点)和SAC-IA(随机一致性),用于实现点云的配准。 6. 点云分割:点云分割是将点云分成多个不同的部分或对象的过程。PCL提供了各种分割算法,例如基于颜色、法线、平面模型等的分割算法。 7. 点云配准和分割的应用:学习如何将点云配准和分割应用于实际问题,例如机器人导航、三维重建和目标检测等。 在学习PCL时,你可以通过阅读PCL官方文档、实践示例代码和参加相关培训课程等方式来深入了解和掌握PCL库的使用。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值