【ZED】从零开始使用ZED相机(三):深度图与点云数据的实战解析

张开发
2026/4/14 2:06:15 15 分钟阅读

分享文章

【ZED】从零开始使用ZED相机(三):深度图与点云数据的实战解析
1. 深度图与点云数据的基础认知第一次拿到ZED相机时最让我兴奋的就是它能直接输出深度图和点云数据。深度图看起来就像一张灰度图但每个像素值实际上代表了物体到相机的距离单位通常是毫米。我习惯用手机拍张普通照片对比着看——普通照片记录颜色深度图记录空间关系。点云数据就更神奇了它把二维的深度图扩展成了三维坐标集合。每个点除了XYZ坐标还能携带RGB颜色信息。有次我对着书架扫描导出的点云文件在电脑里旋转查看时连书本之间的缝隙都清晰可见。不过要注意点云密度和精度会受相机分辨率、物体材质比如反光表面的影响。2. 深度图获取的实战技巧2.1 参数配置的黄金组合经过多次测试我发现这几个参数对深度图质量影响最大depth_mode: 推荐ULTRA模式需要GPU支持在RTX3060上能稳定跑30FPSdepth_minimum_distance: 默认0.3米如果主要拍摄近物可调到0.1米depth_maximum_distance: 室内场景建议设5-10米超出后精度会显著下降init_params sl.InitParameters() init_params.depth_mode sl.DEPTH_MODE.ULTRA # 深度模式 init_params.coordinate_units sl.UNIT.MILLIMETER # 使用毫米单位 init_params.depth_minimum_distance 500 # 最近0.5米 init_params.depth_maximum_distance 5000 # 最远5米2.2 深度图的后处理原始深度图可能有噪点我常用中值滤波配合形态学处理# 获取原始深度图 zed.retrieve_measure(depth_map, sl.MEASURE.DEPTH) depth_data depth_map.get_data() # 后处理 processed_depth cv2.medianBlur(depth_data, 5) # 5x5中值滤波 kernel np.ones((3,3), np.uint8) processed_depth cv2.morphologyEx(processed_depth, cv2.MORPH_CLOSE, kernel)注意后处理会消耗计算资源实时应用时需要测试帧率是否达标3. 点云数据的进阶玩法3.1 完整点云采集流程采集高质量点云的关键是控制移动速度。我总结的经验是保持相机匀速移动约0.3m/s避免剧烈旋转对同一区域多次扫描point_cloud sl.Mat() while True: if zed.grab() sl.ERROR_CODE.SUCCESS: zed.retrieve_measure(point_cloud, sl.MEASURE.XYZRGBA) # 转换为NumPy数组 pc_array point_cloud.get_data() # 保存为PLY格式 sl.save_with_point_cloud(scan.ply, pc_array)3.2 点云压缩与可视化原始点云数据量很大我常用体素网格滤波降采样from open3d import voxel_down_sample # 加载点云 pcd o3d.io.read_point_cloud(scan.ply) # 体素降采样5mm立方体保留一个点 down_pcd voxel_down_sample(pcd, voxel_size5) # 保存 o3d.io.write_point_cloud(compressed.ply, down_pcd)在Jupyter里用pyntcloud快速查看from pyntcloud import PyntCloud cloud PyntCloud.from_file(compressed.ply) cloud.plot(initial_point_size0.1)4. 典型应用场景解析4.1 室内三维重建实战去年我用ZED给工作室做三维重建时摸索出一套有效流程先进行相机标定ZED出厂已标定但建议定期检查沿着墙面走Z字形路径扫描用ICP算法对齐多帧点云关键代码片段# 多帧点云配准 def align_point_clouds(target, source): icp_coarse o3d.pipelines.registration.registration_icp( source, target, max_correspondence_distance0.05, estimation_methodo3d.pipelines.registration.TransformationEstimationPointToPoint()) icp_fine o3d.pipelines.registration.registration_icp( source, target, max_correspondence_distance0.02, estimation_methodo3d.pipelines.registration.TransformationEstimationPointToPoint(), initicp_coarse.transformation) return icp_fine.transformation4.2 动态物体追踪方案结合深度图和点云可以实现更稳定的物体追踪。我在一个机械臂分拣项目中这样实现在RGB图像中用YOLO检测目标提取对应区域的点云计算质心通过连续帧的质心移动判断运动轨迹# 计算点云质心 def get_cloud_center(pc_array, mask): masked_pc pc_array[mask] valid_points masked_pc[~np.isnan(masked_pc).any(axis1)] return np.mean(valid_points, axis0)5. 避坑指南与性能优化5.1 常见问题排查遇到过最头疼的问题是深度图出现条纹噪声后来发现是环境光过强时关闭相机的自动曝光避免拍摄纯色墙面增加特征点更新到最新版SDKv3.8后改进了深度算法5.2 性能优化技巧在树莓派上跑ZED时这些调整能让帧率提升3倍改用DEPTH_MODE.PERFORMANCE模式分辨率降到720p启用enable_positional_tracking时会占用资源不需要SLAM时关闭# 轻量级配置示例 init_params sl.InitParameters() init_params.camera_resolution sl.RESOLUTION.HD720 init_params.depth_mode sl.DEPTH_MODE.PERFORMANCE init_params.coordinate_units sl.UNIT.MILLIMETER实际项目中我会先获取低分辨率深度图做快速检测再对感兴趣区域进行高精度扫描。这种两级处理方式在物流分拣系统中特别有效既能保证实时性又能准确定位包裹位置。

更多文章