使用 Open3D 批量渲染并导出固定视角点云截图
一、前言
在三维点云处理与可视化中,固定视角批量生成点云渲染截图是一个常见的需求。例如,想要将同一系列的点云(PCD 文件)在同样的视角下生成序列图片,以便后续合成为视频或进行其他可视化演示。本文将介绍如何使用 Python + Open3D 实现批量加载 PCD 文件、设置统一的相机视角,并导出渲染截图。
二、环境准备
- Python 环境:建议使用 Python 3.7+。
- Open3D 库:本文使用的是
open3d和open3d.visualization.gui。安装方式如下:pip install open3d - 其他依赖库:
numpypickleglobtimeos
如果缺少对应的库,使用pip install 库名即可。
三、代码解析
下面的代码分为几个主要部分:
- 相机矩阵转换:将 Open3D 的模型矩阵转换为外参矩阵。
- 相机内参生成:根据视口大小与视场角(FOV)生成相机内参。
- 保存与加载相机视角:使用
pickle将当前相机的内外参持久化保存,方便在下次使用时快速恢复相机位置。 - 批量处理函数:遍历指定文件夹下所有
.pcd文件,加载点云、应用相机视角、并自动保存渲染截图。 - 主函数:在
if __name__ == "__main__":中调用批处理函数,或先进行单独的相机视角设置保存操作。
完整代码如下(可直接复制使用):
import numpy as np
import open3d as o3d
import open3d.visualization.gui as gui
from pickle import load, dump
import os
import glob
import time# 用于将坐标系转换为OpenGL风格
ToGLCamera = np.array([[1, 0, 0, 0],[0, -1, 0, 0],[0, 0, -1, 0],[0, 0, 0, 1]
])
FromGLGamera = np.linalg.inv(ToGLCamera)def model_matrix_to_extrinsic_matrix(model_matrix):"""将Open3D的model_matrix转换为外参矩阵"""return np.linalg.inv(model_matrix @ FromGLGamera)def create_camera_intrinsic_from_size(width=1024, height=768, hfov=60.0, vfov=60.0):"""根据视口大小与水平/垂直FOV生成相机内参"""fx = (width / 2.0) / np.tan(np.radians(hfov) / 2)fy = (height / 2.0) / np.tan(np.radians(vfov) / 2)return np.array([[fx, 0, width / 2.0],[0, fy, height / 2.0],[0, 0, 1]])def save_view(vis, fname='saved_view.pkl'):"""保存当前可视化窗口的相机视角(内参、外参、图像尺寸)"""try:model_matrix = np.asarray(vis.scene.camera.get_model_matrix())extrinsic = model_matrix_to_extrinsic_matrix(model_matrix)width, height = vis.size.width, vis.size.heightintrinsic = create_camera_intrinsic_from_size(width, height)saved_view = dict(extrinsic=extrinsic, intrinsic=intrinsic, width=width, height=height)with open(fname, 'wb') as pickle_file:dump(saved_view, pickle_file)print(f"Camera view saved to {fname}")except Exception as e:print("Error saving view:", e)def load_view(vis, fname="saved_view.pkl"):"""加载已保存的相机视角(内参、外参、图像尺寸)"""try:with open(fname, 'rb') as pickle_file:saved_view = load(pickle_file)vis.setup_camera(saved_view['intrinsic'], saved_view['extrinsic'],saved_view['width'], saved_view['height'])print(f"Camera view loaded from {fname}")except Exception as e:print("Can't load view file:", e)def process_pcd_folder(input_folder, output_folder, view_file='saved_view.pkl'):"""批量处理文件夹中的所有 PCD 文件,应用指定视角并保存截图"""os.makedirs(output_folder, exist_ok=True)pcd_files = sorted(glob.glob(os.path.join(input_folder, "*.pcd")))if not pcd_files:print(f"No PCD files found in {input_folder}")returnprint(f"Found {len(pcd_files)} PCD files")# 初始化GUIgui.Application.instance.initialize()vis = o3d.visualization.O3DVisualizer("PCD Batch Renderer", 1920, 1080)gui.Application.instance.add_window(vis)# 设置渲染参数vis.point_size = 4vis.show_axes = Falsevis.show_skybox(False)def process_next(idx):if idx >= len(pcd_files):print("Batch processing completed!")gui.Application.instance.quit()returnpcd_file = pcd_files[idx]print(f"Processing {idx+1}/{len(pcd_files)}: {os.path.basename(pcd_file)}")try:# 加载点云文件pcd = o3d.io.read_point_cloud(pcd_file)geom_name = f"PointCloud_{idx}"# 清除之前所有几何体,确保内存资源不会累积if idx > 0:vis.remove_geometry(f"PointCloud_{idx-1}")vis.add_geometry(geom_name, pcd)# 加载预先保存的视角load_view(vis, view_file)# 构建输出路径base_name = os.path.splitext(os.path.basename(pcd_file))[0]output_path = os.path.join(output_folder, f"{base_name}.png")def take_screenshot():# 延迟1秒以确保视角和渲染完全加载time.sleep(1)vis.export_current_image(output_path)print(f"Screenshot saved to {output_path}")# 处理完当前文件后,处理下一个process_next(idx + 1)# 使用post_to_main_thread确保截图任务在GUI线程执行gui.Application.instance.post_to_main_thread(vis, take_screenshot)except Exception as e:print(f"Error processing {pcd_file}: {e}")# 出错时跳过当前文件,继续下一个process_next(idx + 1)# 开始处理第一个文件process_next(0)gui.Application.instance.run()def batch_process():"""主函数:指定输入、输出文件夹以及相机视角文件,然后进行批量处理"""input_folder = './input'output_folder = './screenshots'os.makedirs(output_folder, exist_ok=True)view_file = 'saved_view.pkl'process_pcd_folder(input_folder, output_folder, view_file)if __name__ == "__main__":# 若需要先设置视角,运行 save_view 所在的逻辑# 若已设置好视角,运行 batch_process()批量处理batch_process()
1. 代码主要流程
- 读取文件列表:通过
glob.glob获取指定文件夹下的所有.pcd文件并排序。 - 初始化 Open3D GUI:使用
O3DVisualizer进行可视化。 - 循环处理每个 PCD:
- 读取点云数据
pcd = o3d.io.read_point_cloud(...) - 加载之前保存的视角参数
load_view(vis, view_file) - 设置几何体到渲染窗口
- 通过
vis.export_current_image(...)将当前视图截图保存
- 读取点云数据
- 处理结束后退出:当全部
.pcd文件处理完毕,自动退出 GUI。
2. 视角保存与加载
save_view(vis, fname='saved_view.pkl'):从当前的vis.scene.camera获取model_matrix,然后计算外参矩阵、内参矩阵并存储到一个字典中,通过pickle持久化到saved_view.pkl文件。load_view(vis, fname='saved_view.pkl'):从文件中读取上述字典,调用vis.setup_camera(...)将相机恢复到保存时的视角。
这样做的好处是,我们可以先交互式地在 Open3D 中调整一个理想的点云视角,然后保存该视角。后续就可以用同样的参数去渲染其他点云,实现“统一视角”输出。
3. 视角设置的两种方式
- 先在单个点云上用脚本交互式设置并保存:
- 先运行一个类似的脚本,只加载一个点云,不做批处理。
- 在界面中使用鼠标旋转/平移点云至理想位置,然后调用
save_view(vis)。
- 直接修改代码中的相机参数:如果你对内参、外参很熟悉,也可以直接硬编码想要的矩阵。
四、使用说明
- 准备 PCD 文件:将所有需要处理的
.pcd文件放在同一个文件夹中。 - 保存视角(可选):
- 若你已知道要使用的视角参数,可以跳过这一步;否则先写个简单脚本,加载一两个 PCD 文件后,通过交互操作找到满意的视角,执行
save_view(vis)。 - 此时会生成一个
saved_view.pkl文件,里面记录了相机的内外参。
- 若你已知道要使用的视角参数,可以跳过这一步;否则先写个简单脚本,加载一两个 PCD 文件后,通过交互操作找到满意的视角,执行
- 运行批处理:
- 修改
batch_process()中的input_folder和output_folder为你的输入、输出路径。 - 运行脚本后,Open3D 窗口会依次加载每个
.pcd,应用保存好的视角,然后自动截图并存储到output_folder中。
- 修改
在所有点云都处理完后,你就能在输出文件夹下看到对应的 .png 文件序列。
五、结果展示
下面是一张示例截图,展示了点云在固定视角下的渲染效果(仅做示意,非实际数据):

六、后续扩展
- 生成视频:如果想将渲染好的序列图片合成为视频,可使用
ffmpeg,示例命令如下:
其中ffmpeg -framerate 10 -i labeled_sync_frame_%03d.png -c:v libx264 -pix_fmt yuv420p output.mp4-framerate 10表示每秒 10 帧,可根据需要调整。 - 更多可视化选项:如改变
point_size、背景颜色、或添加坐标轴等,可参考 Open3D 文档或修改O3DVisualizer的属性。 - 其他文件格式:如果想批量处理
.ply或.xyz,只需要在代码中修改对应的读取方式,以及glob.glob匹配模式即可。
七、总结
通过上述方法,可以轻松地在同一视角下对多份点云进行批量渲染和截图,适用于制作点云动画、对比分析等场景。核心思想是事先保存好相机参数,并在批处理过程中为每个点云恢复相同的内外参,保证输出图像的视角一致。希望对你的三维可视化工作有所帮助,欢迎交流讨论!
相关文章:
使用 Open3D 批量渲染并导出固定视角点云截图
一、前言 在三维点云处理与可视化中,固定视角批量生成点云渲染截图是一个常见的需求。例如,想要将同一系列的点云(PCD 文件)在同样的视角下生成序列图片,以便后续合成为视频或进行其他可视化演示。本文将介绍如何使用…...
汽车无钥匙进入一键启动操作正确步骤
汽车智能无钥匙进入和一键启动的技术在近年来比较成熟,不同车型的操作步骤可能略有不同,但基本的流程应该是通用的,不会因为时间变化而有大的改变。 移动管家汽车一键启动无钥匙进入系统通常是通过携带钥匙靠近车辆,然后触摸门把…...
JMeter 的基础知识-安装部分
以下将从环境配置开始,为你详细介绍 JMeter 的基础知识,涵盖环境搭建、界面认知、测试计划创建、常用组件使用等方面内容。 1. 环境配置 1.1 安装 Java JMeter 是基于 Java 开发的,所以需要先安装 Java 开发工具包(JDK)。 下载 JDK:访问 Oracle 官方网站(https://www…...
解决后端跨域问题
目录 一、什么是跨域问题? 1、跨域问题的定义 2、举例 3、为什么会有跨域问题的存在? 二、解决跨域问题 1、新建配置类 2、编写代码 三、结语 一、什么是跨域问题? 1、跨域问题的定义 跨域问题(Cross-Origin Resource Sh…...
补题A-E Codeforces Round 953 (Div. 2)
https://codeforces.com/contest/1979 A. Guess the Maximum 原题链接:https://codeforces.com/contest/1979/problem/A 求相邻元素的最大值的最小值。 #include <bits/stdc.h> using namespace std; #define IOS ios::sync_with_stdio(0), cin.tie(0), cout…...
【WordPress】发布文章时自动通过机器人推送到钉钉
在您的主题下functions.php中添加如下代码: function wpso_dingding_publish_notify($post_ID) {// 获取文章对象$post get_post($post_ID);// 检查是否是文章首次发布(即不是修订版)if (get_post_status($post_ID) publish && !g…...
鸿蒙开发深入浅出04(首页数据渲染、搜索、Stack样式堆叠、Grid布局、shadow阴影)
鸿蒙开发深入浅出04(首页数据渲染、搜索、Stack样式堆叠、Grid布局、shadow阴影) 1、效果展示2、ets/pages/Home.ets3、ets/views/Home/SearchBar.ets4、ets/views/Home/NavList.ets5、ets/views/Home/TileList.ets6、ets/views/Home/PlanList.ets7、后端…...
管道文件(1)
1.无名管道:在同一主机下,具有亲缘关系的进程间的通信,如父子进程间的通信。 2.有名管道:在同一主机下的任意进程间的通信。 (1)管道的创建 (2)管道的打开(openÿ…...
什么是AI agent技术,有哪些著名案例
AI Agent技术是一种基于人工智能的智能实体,能够感知环境、进行决策和执行动作,以实现特定目标。近年来,随着大模型(如GPT-4)和生成式AI技术的发展,AI Agent在多个领域得到了广泛应用,并取得了显…...
Cursor结合Claude 3.7零基础开发愤怒的小鸟【深夜Claude 3.7系列发布,类似DeepSeek-R1和V3的合体?】
文章目录 前言介绍“市面上唯一的混合模型”卓越的编程能力、精准控制思考时间Cursor已接入Cursor结合Claude 3.7快速编写游戏完整html代码 🍃作者介绍:双非本科大四网络工程专业在读,阿里云专家博主,前三年专注于Java领域学习&am…...
基于 Python 的天气数据分析与可视化
基于 Python 的天气数据分析与可视化 1. 项目背景 天气数据分析与可视化项目旨在通过爬取天气数据并进行分析,生成可视化图表,帮助用户了解天气变化趋势。通过该项目,学生可以掌握 Python 的数据爬取、数据分析和可视化技能。该项目适用于气…...
Bybit事件技术分析
事件概述 2025年2月21日UTC时间下午02:16:11,Bybit的以太坊冷钱包(0x1db92e2eebc8e0c075a02bea49a2935bcd2dfcf4)因恶意合约升级遭到资金盗取。根据Bybit CEO Ben Zhou的声明,攻击者通过钓鱼攻击诱骗冷钱包签名者错误签署恶意交易…...
JavaWeb-在idea中配置Servlet项目
文章目录 在idea中进行Servlet项目的配置(较新的idea版本)创建一个空的JavaSE项目(Project)创建一个普通的JavaSE板块(module)添加Web项目的配置定义一个对象模拟实现接口在web.xml中配置路径映射配置项目到Tomcat服务器启动Tomcat服务器进行测试 在idea中进行Servlet项目的配置…...
redis小记
redis小记 下载redis sudo apt-get install redis-server redis基本命令 ubuntu16下的redis没有protected-mode属性,就算sudo启动,也不能往/var/spool/cron/crontabs写计划任务,感觉很安全 #连接到redis redis-cli -h 127.0.0.1 -p 6379 …...
垂类大模型微调(一):认识LLaMA-Factory
LlamaFactory 是一个专注于 高效微调大型语言模型(LLMs) 的开源工具框架,尤其以支持 LLaMA(Meta 的大型语言模型系列)及其衍生模型(如 Chinese-LLaMA、Alpaca 等)而闻名。它的目标是简化模型微调流程,降低用户使用门槛; 官方文档 一、介绍 高效微调支持 支持多种微调…...
企业为什么要选择软件测试外包公司?湖南软件测试公司有哪些?
在当今快速发展的技术背景下,软件测试已成为软件开发生命周期的重要一环。随着企业对软件质量要求的不断提高,软件测试外包公司逐渐被越来越多的企业所青睐。 软件测试外包公司通过将软件测试从内部团队外包出去,帮助企业减少开发成本、提升…...
数据保护API(DPAPI)深度剖析与安全实践
Windows DPAPI 安全机制解析 在当今数据泄露与网络攻击日益频繁的背景下,Windows 提供的 DPAPI(Data Protection API)成为开发者保护本地敏感数据的重要工具。本文将从 双层密钥体系、加密流程、跨上下文加密、已知攻击向量与防御措施、企业…...
java23种设计模式-桥接模式
桥接模式(Bridge Pattern)学习笔记 🌟 定义 桥接模式属于结构型设计模式,将抽象部分与实现部分分离,使它们可以独立变化。通过组合代替继承的方式,解决多维度的扩展问题,防止类爆炸。 &#x…...
3D Web轻量化引擎HOOPS Communicator如何赋能航空航天制造?
在当今航空航天制造领域,精确度、效率和协作是推动行业发展的关键要素。随着数字化技术的飞速发展,3D Web可视化开发包HOOPS Communicator 为航空航天制造带来了革命性的变化。它凭借强大的功能和灵活的应用,助力企业在设计、生产、培训等各个…...
iOS手机App爬虫- (1) Mac安装Appium真机运行环境
iOS手机App爬虫 一、环境准备与工具安装1. 开发基础环境配置1.1 Node.js环境1.2 Xcode套件1.3 Java环境 2. 核心测试工具链2.1 Appium主程序2.2 辅助工具集 3. 可视化工具 二、设备与环境验证1. 设备信息获取2. 环境健康检查 三、WebDriverAgent编译部署1. 设备端准备2. 项目配…...
MPNet:旋转机械轻量化故障诊断模型详解python代码复现
目录 一、问题背景与挑战 二、MPNet核心架构 2.1 多分支特征融合模块(MBFM) 2.2 残差注意力金字塔模块(RAPM) 2.2.1 空间金字塔注意力(SPA) 2.2.2 金字塔残差块(PRBlock) 2.3 分类器设计 三、关键技术突破 3.1 多尺度特征融合 3.2 轻量化设计策略 3.3 抗噪声…...
Qt/C++开发监控GB28181系统/取流协议/同时支持udp/tcp被动/tcp主动
一、前言说明 在2011版本的gb28181协议中,拉取视频流只要求udp方式,从2016开始要求新增支持tcp被动和tcp主动两种方式,udp理论上会丢包的,所以实际使用过程可能会出现画面花屏的情况,而tcp肯定不丢包,起码…...
循环冗余码校验CRC码 算法步骤+详细实例计算
通信过程:(白话解释) 我们将原始待发送的消息称为 M M M,依据发送接收消息双方约定的生成多项式 G ( x ) G(x) G(x)(意思就是 G ( x ) G(x) G(x) 是已知的)࿰…...
【Redis技术进阶之路】「原理分析系列开篇」分析客户端和服务端网络诵信交互实现(服务端执行命令请求的过程 - 初始化服务器)
服务端执行命令请求的过程 【专栏简介】【技术大纲】【专栏目标】【目标人群】1. Redis爱好者与社区成员2. 后端开发和系统架构师3. 计算机专业的本科生及研究生 初始化服务器1. 初始化服务器状态结构初始化RedisServer变量 2. 加载相关系统配置和用户配置参数定制化配置参数案…...
跨链模式:多链互操作架构与性能扩展方案
跨链模式:多链互操作架构与性能扩展方案 ——构建下一代区块链互联网的技术基石 一、跨链架构的核心范式演进 1. 分层协议栈:模块化解耦设计 现代跨链系统采用分层协议栈实现灵活扩展(H2Cross架构): 适配层…...
css3笔记 (1) 自用
outline: none 用于移除元素获得焦点时默认的轮廓线 broder:0 用于移除边框 font-size:0 用于设置字体不显示 list-style: none 消除<li> 标签默认样式 margin: xx auto 版心居中 width:100% 通栏 vertical-align 作用于行内元素 / 表格单元格ÿ…...
服务器--宝塔命令
一、宝塔面板安装命令 ⚠️ 必须使用 root 用户 或 sudo 权限执行! sudo su - 1. CentOS 系统: yum install -y wget && wget -O install.sh http://download.bt.cn/install/install_6.0.sh && sh install.sh2. Ubuntu / Debian 系统…...
Xen Server服务器释放磁盘空间
disk.sh #!/bin/bashcd /run/sr-mount/e54f0646-ae11-0457-b64f-eba4673b824c # 全部虚拟机物理磁盘文件存储 a$(ls -l | awk {print $NF} | cut -d. -f1) # 使用中的虚拟机物理磁盘文件 b$(xe vm-disk-list --multiple | grep uuid | awk {print $NF})printf "%s\n"…...
通过 Ansible 在 Windows 2022 上安装 IIS Web 服务器
拓扑结构 这是一个用于通过 Ansible 部署 IIS Web 服务器的实验室拓扑。 前提条件: 在被管理的节点上安装WinRm 准备一张自签名的证书 开放防火墙入站tcp 5985 5986端口 准备自签名证书 PS C:\Users\azureuser> $cert New-SelfSignedCertificate -DnsName &…...
系统掌握PyTorch:图解张量、Autograd、DataLoader、nn.Module与实战模型
本文较长,建议点赞收藏,以免遗失。更多AI大模型应用开发学习视频及资料,尽在聚客AI学院。 本文通过代码驱动的方式,系统讲解PyTorch核心概念和实战技巧,涵盖张量操作、自动微分、数据加载、模型构建和训练全流程&#…...
