写这系列教程的第四篇之前,我其实犹豫了很久要不要把 RVIZ 单独拿出来讲。后来在实验室调一台差速小车的时候想明白了:你让轮子转起来、电机嗡一声开始跑,这个过程代码量并不大,真正折磨人的是“车为什么没按预想轨迹走”。日志打印一堆坐标数字,看得眼睛疼,最后还是得打开 RVIZ 把 TF、激光点云、路径全部叠出来,一眼定位问题。所以这篇我打算把 RVIZ 彻底掰开揉碎讲一遍,从“它到底是干什么的”讲到“打不开、显示不出点云怎么办”,适合刚装完 ROS 还在迷茫期的初学者,也适合已经写过几个话题、想系统梳理可视化技巧的同学。
这篇主要基于 Ubuntu 20.04 + ROS Noetic 的操作界面来写,最后会用一节专门讲 ROS 2(尤其是 Humble)环境下 RVIZ2 的差异。不管你是正准备跟着网上的教程装环境,还是已经在 Ubuntu 22.04 上装好了 Humble,都可以对照着操作。文章里出现的命令、界面按钮、参数含义,都是我实际敲过、点过的,你可以直接抄作业。
1. RVIZ 到底是什么,它凭什么是 ROS 的门面
1.1 从“看不见的控制”到“能看见的调试台”
你装好 ROS、跑起来一个节点、订阅一个话题,其实数据都在内存里流动。速度、角度、坐标、点云这些信息用rostopic echo也能在终端里看到,但全是数字,人脑对数字的感知能力极其有限。RVIZ 干的事情,说白了就是把 ROS 里流动的数据“翻译”成三维场景:机器人模型显示成 3D 模型,激光雷达数据变成密密麻麻的点,代价地图变成一张可交互的二维格子,路径变成一条带箭头的曲线。
这套思路跟“你怎么判断一台电脑卡不卡”是同一个逻辑。你不会去读 CPU 寄存器的值,而是直接看任务管理器里的曲线。RVIZ 就是 ROS 世界的任务管理器,只不过它渲染的是空间数据。很多教程把它放在很靠后的位置讲,我觉得不对,RVIZ 应该在你学完rosnode、rostopic之后马上接触,因为它能帮你直观理解那些抽象概念。
1.2 RVIZ 能显示什么、不能显示什么
RVIZ 能显示的数据类型非常广,常见的有这几种:
- TF 坐标变换:机器人的每个关节、传感器在世界坐标系下的位置关系
- LaserScan:二维激光雷达的一圈扫描点
- PointCloud2:三维点云,比如深度相机、三维激光雷达
- RobotModel:机器人的 URDF 模型,跟着 TF 实时运动
- Path:导航规划出来的路径轨迹
- Marker / MarkerArray:你可以在任意坐标画箭头、方块、文字,做调试标记
- Image / Camera:图像话题,可以直接嵌在界面上
- Map:栅格地图
但要注意,RVIZ 不是仿真器,它自己不会产生数据。开着 RVIZ 如果屏幕上空空如也,不是程序坏了,而是没有节点向话题发数据。所以后面实操部分,我会带着你用rosbag和rostopic pub造数据、录数据,让场景先“活”起来,再谈显示配置。
2. 环境准备:先把 RVIZ 跑起来再说
2.1 检查 RVIZ 是否安装好
如果你是用 apt 完整安装的ros-noetic-desktop-full,RVIZ 已经包含在内了,不需要额外装。但如果当时只装了基础版ros-noetic-ros-base,就需要手动补一个包:
sudo apt install ros-noetic-rvizROS 2 Humble 对应的是:
sudo apt install ros-humble-rviz2安装完成后,先确认一下环境变量是否已经加载。每次开新终端,建议养成习惯:
source /opt/ros/noetic/setup.bash如果觉得每次输太麻烦,直接写进~/.bashrc末尾,后面所有终端都会自动生效。这一步经常会有人漏掉,结果敲rviz提示 command not found,我还见过有同学以为是安装失败,又把系统重装了一遍,其实就一行 source 的事。
有些刚入门的朋友用的是网上一键安装脚本,比如鱼香ROS的自动安装工具。我没法替作者担保,但实测给两台干净的 Ubuntu 20.04 机器装过,它对系统版本判断得很准,装出来的 ROS 环境、依赖库都齐全,连~/.bashrc都会帮你配好。如果你在手动配置源、添加密钥那一步反复出错,用社区维护的脚本确实能省下不少时间。装完记得验证:
rosversion -d能输出noetic或者humble,就说明环境基本正常。
2.2 第一次启动,竟然黑屏了?
在终端里输入rviz,正常会弹出一个三维界面,默认视角是 XYZ 坐标轴交叉在正中心,背景是深灰色,左侧是显示列表(Displays),上面是一个工具栏。80% 的情况下第一次启动都能成功,但剩下 20% 的情况会把你卡住,最常见的两个坑在虚拟机和新装好的笔记本上:
第一个是虚拟机黑屏。如果你用 VMware 或 VirtualBox 装的 Ubuntu,进 RVIZ 后可能看到图形窗口一片黑,或者直接报错Could not initialize OpenGL。这是因为虚拟机默认没有开启 3D 加速。
解决办法:
- VMware:虚拟机设置 → 显示器 → 勾选“加速 3D 图形”
- VirtualBox:虚拟机设置 → 显示 → 显卡控制器选 VBoxSVGA,显存拉到最大,并且勾选“启用 3D 加速”
改完重启虚拟机,一般就能正常显示。
第二个是实机上的显卡驱动问题。NVIDIA 显卡如果没有正确安装驱动,RVIZ 会尝试用 Mesa 软件渲染,卡到鼠标都挪不动。先检查:
nvidia-smi如果提示 command not found,说明驱动没装好。在“软件和更新”里切到“附加驱动”选项卡,选一个 recommended 的闭源驱动装上,重启后一般就能用上硬件加速。实在折腾不明白,可以在启动 RVIZ 前设置一个环境变量,强制走软件渲染:
export LIBGL_ALWAYS_SOFTWARE=1 rviz这招治标不治本,但能让你先把界面跑起来,不算白折腾。
3. 界面拆解:对着图把每个区块认全
3.1 五大区域的划分与作用
RVIZ 启动后,默认布局可以分成五个区域:顶部的工具栏、左侧的显示列表(Displays)、中间最大的 3D 视图区、底部的状态栏(Status)、以及右侧可折叠的工具属性面板。我第一次用的时候只顾着盯中间的三维视图,觉得其它都是摆设,用久了才发现,真正决定你能不能高效调车的是左侧那块列表。
顶部的工具栏有几个常用按钮:
- Interact(M):切换为交互模式,可以拖动带有交互标记的物体
- Move Camera(F):默认模式,用鼠标旋转、平移、缩放视角
- Select:点击选中物体,显示它的属性
- 2D Pose Estimate / 2D Nav Goal:在机器人导航调试中用来给定初始位姿和目标点
- Measure:量两点之间的距离
- Publish Point:向
/clicked_point话题发布你点击的坐标
底下还有一个 Time 显示区,长这样:
Time: 123.45 ROS Time: 123.45 Wall Time: 2024-01-01 12:00:00ROS Time是 ROS 节点内部的时间,Wall Time是机器人的实际系统时间。如果你在回放 rosbag,ROS Time会跟着 bag 里的时间戳走,而Wall Time不走。这个区别后面排查点云不动的问题时会用到。
最底部状态栏会显示当前插件、帧率、选中的物体坐标。平时不太注意它,但一旦你的 TF 配置出错,红色警告会直接砸到这里,所以写代码的时候我也会时不时瞟一眼状态栏。
3.2 Displays 树:整个 RVIZ 的控制核心
左侧 Displays 面板,是所有显示元素的集合。它是一棵树,每个条目代表一种显示类型。默认只有一个Grid(地面网格),其余都是空的。点击左下角Add按钮,会弹出两个标签页:
- By display type:按显示类型选,比如 LaserScan、PointCloud2、RobotModel
- By topic:按话题选,RVIZ 会扫描当前所有活跃话题,自动匹配可用的显示类型
新手建议直接用By topic来加,因为它会把Fixed Frame中能收到 TF 的话题自动列出来,你点一下就帮你配好了。加完之后,每一项前面都有复选框,勾选代表显示,取消勾选代表隐藏。这个操作非常像 PS 里的图层,你随时可以关掉不想看的图层。
选中某个显示项后,它下方会展开一堆属性。以 LaserScan 为例:
- Topic:要订阅的话题名
- Size:点的大小,单位米
- Color:点的颜色
- Decay Time:点保持的时长,单位秒,默认 0 表示只显示当前帧
- Color Transformer:可以用激光强度值映射颜色
这些属性具体怎么调,我在第 4 节实操里会说。如果你刚开始用,只需要记住一条:所有显示项的属性修改都是即时生效的,所以你可以边拖参数边看效果,反悔了就恢复默认,完全不会有任何风险。
3.3 Fixed Frame 与视图控制器的“坐标系哲学”
很多同学第一次看到 RVIZ 满屏红色警告,都是因为一句话:
Fixed Frame [map] does not exist这是因为 RVIZ 在做渲染时,必须有一个根坐标系,所有数据都会先变换到这个坐标系下再显示。这个根坐标系就是Fixed Frame,默认叫map,在左上角可以改。如果当前没有任何节点发布map这个坐标系,就会报错。
我一般调试时会把Fixed Frame设成odom或者base_link,这取决于机器人有没有发布对应的 TF。如果你只是在桌面上没有接真实机器人,最简单的办法是发一个静态 TF:
rosrun tf static_transform_publisher 0 0 0 0 0 0 map base_link 100这条命令会发布从map到base_link的静态变换,频率 100Hz。RVIZ 立刻就不报 TF 错误了。这个命令在调试阶段特别常用,我几乎每次启动 RVIZ 都会开一个终端发它,省得老是纠结坐标系对不上。
视图控制器在 RVIZ 里也很关键。默认是Orbit视图,也就是“轨道相机”,鼠标左键拖动旋转,滚轮缩放,右键拖动平移。另一种常用的是TopDownOrtho俯视正交点云,适合看导航地图;还有FPV第一人称视角,适合配合仿真模型看“机身视角”。你可以点界面左上角的下拉框切换。最重要的一个提示:如果想在三维视图里选中某个物体,记得先把工具切到Select模式,否则鼠标右键之类的操作容易误触相机视角,刚入门经常被这个问题搞懵。
4. 实操入门:搭一个带 TF 和传感器的可视化场景
4.1 准备数据:用 rosbag 让界面“活”起来
RVIZ 界面上如果没有数据,就像打开了世界地图却看不到城市一样。偏偏很多教程就直接让你在空场景里手动 Add,结果你加了 LaserScan,中间空空如也,又会陷入“我是不是哪里配错了”的自我怀疑。
我的建议是准备几份 rosbag 数据。你可以从 ROS 官网的示例资源里下载,也可以自己录。自己录一份最简单的,启动一个节点发布模拟激光数据:
rosrun rviz topic_tools # 如果没有这个工具,先安装 ros-noetic-topic-tools不过更直接的是用rostopic pub手动发布一帧数据。比如给/scan发一条 LaserScan 消息,我实际写过这样的命令:
rostopic pub /scan sensor_msgs/LaserScan "header: frame_id: 'laser' angle_min: -3.14159 angle_max: 3.14159 angle_increment: 0.01 range_min: 0.05 range_max: 20.0 ranges: [3.0, 3.1, 3.2, 2.9, 3.3]"这样你就可以在 RVIZ 里看到点云的出现。但很明显,手动发一帧太累。推荐做法是使用系统自带的演示包:
roslaunch turtlebot3_gazebo turtlebot3_world.launch如果你装了 Gazebo 仿真,它会一边跑仿真,一边发布激光、里程计、TF 数据。此时打开 RVIZ,就能看到真实小车在世界里的三维场景。没有装 Gazebo 也不慌,可以用官方自带的rviz演示数据:
rosrun rviz rviz -d /opt/ros/noetic/share/rviz/default.rviz但最终想练熟,还是建议录制自己的数据。录 bga 的步骤很简单:
rosbag record -O my_robot.bag /scan /tf /odom /camera/depth/points-O指定输出文件名,后面跟一组要记录的话题。之后回放:
rosbag play my_robot.bag回放时光标会走,RVIZ 里的数据也会跟着动起来。如果点云没动,先看界面右下角的 Time,确认ROS Time是否在增长。如果ROS Time总停留在 0,说明 bag 里的时间戳是旧的,你可以在播放时加--clock参数并勾选 RVIZ 的Global Options→Fixed Frame下方那个Time选项,顺时针同步时钟。
4.2 添加第一个显示:LaserScan 和 TF
我建议任何初学者第一次上手 RVIZ,先添加两个显示:TF 和 LaserScan。TF 是最基础的坐标系骨架,LaserScan 是最常见的传感器数据,看到这两个一起显示,你就明白了 RVIZ 的基本工作模式。
操作步骤:
- 启动一个发布 TF 的节点,比如
static_transform_publisher,或者启动机器人模型、rosbag - 打开 RVIZ,点击左下角
Add - 选择
By display type,在列表里找到TF,双击添加 - 再回到
Add,在By topic标签页里找到/scan,选中LaserScan,双击添加 - 观察 3D 视图:现在应该能看到灰色的 Grid 网格,每个坐标系轴(红绿蓝三色)挂在各自的位置,还有一圈点云悬在激光雷达坐标系周围
添加 TF 之后,你会看到一堆小坐标轴。它们代表每个已知坐标系的原点位置。如果你想看坐标轴对应的名字,选中TF显示项,把Marker Scale调大一点,再勾上Show Names,坐标轴旁边就会浮出map、odom、base_link、laser这些名称。
这里常见的问题:为什么我添加 LaserScan 之后,点云没有出现在雷达坐标系上,而是飞到几百米外?原因是 RVIZ 要把/scan消息从frame_id: laser变换到Fixed Frame: map。如果map → base_link → laser这条 TF 链路不完整,计算出来的坐标就毫无意义。所以你在调试时,看到点云位置离谱,先别怀疑数据本身,先检查 TF 的 “红色连线” 有没有断开。
检查 TF 的另一种方式是命令行:
rosrun tf view_frames会生成一个frames.pdf,用图形表示当前所有 TF 树。如果树的某些节点单独飘在外面,说明对应变换没有发布。这个工具排查坐标系问题,比肉眼盯 RVIZ 更高效。
4.3 保存配置:不要再每次都手动加显示了
配置好你想要的所有显示项之后,记得保存。在 RVIZ 左上角菜单栏,File→Save Config As,给它起个名字,比如slam_view.rviz。文件的本质是一段 YAML 文本,记录了所有显示项、话题名、Fixed Frame、视角等设置。
保存好了,下次启动直接加载:
rosrun rviz rviz -d slam_view.rviz我一般会把所有常用配置统一放到~/rviz_configs目录里,再配合 shell 别名:
alias rviz_slam='rviz -d ~/rviz_configs/slam_view.rviz'这样每次打开都不用重新点 Add。如果你在多个机器人项目里工作时,配置文件隔离尤其重要。比如室内导航看的是/map,机械臂调试看的是/robot_description,同一个 RVIZ 界面配置完全不同,直接用-d参数切,效率高很多。
还有一个细节:RVIZ 的配置文件是纯文本,你可以用diff对比两个配置文件的差异,也可以用 git 来管理版本。我曾经有一次把参数调崩了,每次打开 RVIZ 都卡成 PPT,最后直接用 git 回滚了配置文件,瞬间恢复。所以,在开始折腾前先 commit 一份配置,是保命习惯。
5. 进阶:点云、机器人模型与 Marker 调试
5.1 PointCloud2 点云可视化的关键参数
三维点云是 RVIZ 里非常有代表性的显示类型。很多从零开始学 ROS 的朋友,第一次接触点云是在做三维建图或者目标检测时,数据量一大,RVIZ 就开始卡。这时候要懂点云显示的调参逻辑。
添加 PointCloud2:Add→By topic→ 找到/camera/depth/points或/velodyne_points,双击。
点云显示需要关注的参数:
Topic:确认指向正确话题Size (m):每个点的大小。对于激光雷达点云,设成 0.03 左右比较清楚;对于深度相机点云,设小一点 0.01 即可,否则像一片雾Decay Time:默认 0,只显示最新帧。如果你要看多帧叠加的效果,可以设成 0.5 或 1,但注意内存会涨Color Transformer:有 FlatColor 和 AxisColor 两种常见模式。FlatColor 全部点用一种颜色,适合看形状;AxisColor 按点所在轴着色,适合看空间分布,一般我会选 FlatColor,再手动调成亮绿色,对比度最高Style:有 Flat Squares、Points、Boxes 等。Points 是纯点、速度最快;Boxes 是方体、更占资源。如果点云数量上百万,用 Points 模式,帧率会好看很多
实测下来,点云显示最卡的一个参数就是Boxes。三维激光雷达的一圈点动辄几十万,如果误设成 Boxes,RVIZ 能直接把 CPU 吃满。我后来都是把 Viewer 的Style固定成 Points,只有需要观察障碍物轮廓时才临时切回 Boxes。
5.2 RobotModel:加载 URDF 显示整个机器人
如果你下载过别人的机器人模型包,或者用 solidworks 导出过 URDF,就可以在 RVIZ 里把整个机器人三维模型显示出来。添加方法:
- 确保你有一个描述机器人的 URDF 文件在参数服务器上,通常是通过
robot_state_publisher加载的 Add→By display type→RobotModel- 双击后,在
Robot Description属性里,确认名称是/robot_description - 如果模型是展开的,但关节一动不动,检查有没有给
robot_state_publisher发布joint_states
官方自动驾驶仿真环境中经常能见到这个效果:你在 RVIZ 里拖动滑块,机器人的手臂或轮子就跟着动。这是因为在RobotModel的显示属性里,Visual Enabled、Collision Enabled、TF等选项可以单独开关。调试机械臂时,只保留Visual Enabled,不勾Collision Enabled,能避免碰撞体积网格挡住视线。
如果你在加载 URDF 后看到模型是红色、灰色相间的方块,多半是 Description 读取失败或 mesh 文件路径缺失。先用命令行验证:
rosparam get /robot_description | head -c 200如果输出为空,说明 URDF 没加载到参数服务器。常见的加载方式:
rosparam load robot.urdf /robot_description或者用 launch 文件里的param标签。对刚接触的同学来说,建议直接跑一次urdf_tutorial的演示,里面自带一个带轮子的模型,能让你第一时间感受 RobotModel 的效果。
5.3 Marker:如何在 RVIZ 里画自己的调试图形
Marker 是 RVIZ 里最灵活的显示类型。你可以在任意坐标画箭头、线、方块、圆柱体、文本,用来标注调试信息。比如在导航代码里,你可以在目标点画一个绿色的箭头,在障碍物位置画一个红色方块,比终端里 print 坐标直观太多了。
示例代码(ROS 1,Python):
#!/usr/bin/env python3 import rospy from visualization_msgs.msg import Marker rospy.init_node('marker_demo') pub = rospy.Publisher('/visualization_marker', Marker, queue_size=10) marker = Marker() marker.header.frame_id = "map" marker.type = Marker.ARROW marker.action = Marker.ADD marker.pose.position.x = 1.0 marker.pose.position.y = 2.0 marker.pose.orientation.w = 1.0 marker.scale.x = 1.0 # 箭头长度 marker.scale.y = 0.2 # 箭头宽度 marker.scale.z = 0.2 # 箭头高度 marker.color.r = 0.0 marker.color.g = 1.0 marker.color.b = 0.0 marker.color.a = 1.0 rate = rospy.Rate(10) while not rospy.is_shutdown(): pub.publish(marker) rate.sleep()在 RVIZ 里添加Marker显示项就可以看到箭头。RVIZ 里 Marker 的 namespace 会自动分组,所以同一类标记可以通过Marker.ns字段归到一个文件夹里,方便批量隐藏。这个功能在做多目标标注时特别有用。
Marker 的发布频率不需要太高,静态目标 1Hz 就够了。如果频繁更新同一 ID 的 Marker,记得设action = Marker.DELETE来删掉旧的,否则界面上会残留残影,看起来特别乱。
5.4 显示图像与相机数据:Image 插件的坑
如果你有摄像头话题/camera/rgb/image_raw,可以直接添加Image显示类型,RVIZ 会在 3D 场景旁边嵌一个 2D 图像窗口。但要注意一个坑:RVIZ 的图像显示默认只显示一张图,而且不会自动刷新视角,你需要确保Image Topic选对,并且在图像窗口里勾选 “Continuous” 或拖动时间轴才能看到实时画面。
有的同学用 USB 摄像头时发现图像在 RVIZ 里显示为灰色,但是用rqt_image_view能看到画面。这通常是因为图像话题的frame_id没有对应的 TF。解决方案要么发布一个静态 TF,要么在图像显示属性里取消勾选Image→Transform相关选项,强制只显示原始图像。这个经验在实践项目中很管用,我看过不少人卡在这一步。
6. ROS 2 时代:RVIZ2 的迁移注意点
6.1 RVIZ2 的安装与界面变化
ROS 2 对应的是 RVIZ2,整体界面和操作逻辑跟 RVIZ 几乎是同一个模子印出来的。但有几个关键区别:
- 启动命令从
rviz变成了rviz2 - 添加显示项时,很多插件名带
_2D后缀,比如Map在 RVIZ2 中叫Map (ROS 2) - 话题名不带
/的时代结束了。ROS 2 的话题和节点名必须满足命名规则,不能随意加斜杠,所以你在By topic里看到的话题列表和 RVIZ 有些差异 - 配置文件的扩展名同样是
.rviz,但内部格式略有变化,所以 RVIZ 的配置不能直接给 RVIZ2 用,需要重新保存一份
安装命令前面已经提过:
sudo apt install ros-humble-rviz2启动:
source /opt/ros/humble/setup.bash rviz26.2 在 RViz2 中调试点云、模型和 TF
RVIZ2 中添加 PointCloud2 的方式几乎一样。如果你用的是 Gazebo + ROS 2 Humble 仿真,点云话题名自带命名空间,比如/camera/depth/points变成了/camera/depth/points,但大多数情况下没有frame_id缺失的问题。
RVIZ2 的 TF 检查工具变成了tf2_tools,包括view_frames和echo。注意 ROS 2 里的静态变换发布命令是:
ros2 run tf2_ros static_transform_publisher 0 0 0 0 0 0 map base_linkRVIZ2 的 Fixed Frame 默认也是map。如果你在 ROS 2 里做单机器人导航,通常需要先运行定位模块或者 amcl,才能让map存在。如果没有定位模块,直接把Fixed Frame改为odom也行。
RVIZ2 里还有一个比较重要的变化:它的 Displays 面板支持折叠保存和插件状态管理,比以前稳定。而且 RVIZ2 的 3D 视图支持 HDR 背景,有些机器上默认带天空盒,看着更炫,但性能开销也更大。如果你在低配机器上跑,可以在Rendering相关选项里把质量调低。
6.3 从 RVIZ 迁移到 RVIZ2 的配置文件
我在迁移过程中踩过一次坑。以前在 RVIZ 里保存好的.rviz配置文件,用rviz2 -d xxx.rviz打开,结果点云全部消失。后来的结论是,不同版本的插件名和默认参数差异很大,直接复用文件会导致插件无法加载。
最稳妥的做法是:在 RVIZ2 里新建一个空白配置,按照之前文章里的步骤重新添加显示项,再另存为新的.rviz文件。不要怕麻烦,重新配一遍也就几分钟,但能避免因为插件名不匹配导致的各种诡异现象。如果你有多个.rviz配置,可以用文本编辑器打开,把里面插件的Class字段抄出来对比,看到差异就明白为什么加载不出来了。
7. 常见问题与排查技巧实录
7.1 热榜第一类问题:rviz 打不开
“rviz 打不开”是搜索量最高的问题,而且它有很多种表现:点击启动后没反应、报错信息一长串、界面弹出来就闪退、或者整个系统卡死。我整理一下我实际遇到过的情况:
第一种:命令找不到rviz: command not found。这种最简单,原因是没装包或者没 source。先确认包装没装:
dpkg -l | grep rviz如果列表为空,就安装。如果装了,检查环境变量:
echo $ROS_PACKAGE_PATH如果是空的,说明setup.bash没生效,重新 source 一下。
第二种:启动后黑屏闪退。这种常见于双显卡笔记本和虚拟机。先看报错:
rviz如果输出里有Could not initialize OpenGL、libGL error或者Segmentation fault,基本上就是显卡问题。按我在 2.2 节写的思路:虚拟机开 3D 加速,实机装闭源驱动。低配机器可以试:
export LIBGL_ALWAYS_SOFTWARE=1 rviz先跑起来再说。如果这样能开,那就说明是显示驱动的问题,而不是 ROS 配置问题。
第三种:远程 SSH 到机器人上运行 RVIZ,提示cannot open display。这是没有把图形界面转发出来的问题。常规做法是退出再连:
ssh -X username@robot_ip rviz如果还是不行,看看是不是服务器端没装 xauth。真实使用中,我都推荐直接在机器人或者仿真主机本地开 RVIZ,远程调试只会增加排查难度。
7.2 热榜第二类问题:TF 与坐标系疯狂报错
TF 报错是初学者最痛苦的经历之一。常见报错:
Fixed Frame [map] does not existCould not transform from [laser] to [map]No transform between [base_link] and [odom]
这些错误可以总结成一句话:你要显示的数据所在的坐标系,和 Fixed Frame 之间,缺少一条完整的 TF 变换链。
排查步骤:
- 看 RVIZ 里 TF 显示项,哪些坐标轴是红色、哪些是绿色
- 绿色代表有 TF 连接,红色代表断链,或者根本没有发布
- 用命令行:
rosrun tf tf_echo map base_link如果输出:
Exception thrown: "base_link" passed to lookupTransform argument target_frame does not exist.那就说明base_link根本没有被发布。检查你的 robot_state_publisher、里程计节点是否正常启动。
- 如果是在运动过程中时断时通,多半是 TF 消息发布频率太低,或者节点崩了又重启导致时间戳跳跃。用:
rosrun tf view_frames看看 TF 树的叶子节点是否稳定挂在树上。
静态坐标还有一种发布方式叫tf2_ros::StaticTransformBroadcaster,适合发布相机到车体底座这类不会变的坐标系。我给相机标定的时候就用它,效果比每帧发 TF 稳定得多。
7.3 看不到点云或图像,但话题里明明有数据
这种问题最气人。你先rostopic list看到话题在,rostopic hz /scan也有频率,但 RVIZ 里就是什么都不显示。
这时候按以下顺序排查:
- 确认
Fixed Frame和数据的frame_id是否一致或有 TF 链。最快的验证方法:把 LaserScan 的话题双击打开,看属性里的Topic颜色。如果话题名旁边有个红色感叹号,大概率是 TF 错误,RVIZ 收到了消息但无法转换坐标。 - 看一下 Displays 面板中该显示项前面的复选框是否勾上。有时候不小心按到快捷键把图层隐藏了,这种事我干过不止一次。
- 检查
Status状态栏。RVIZ 会用红色Error或黄色Warning告诉你为什么没显示。点开错误详情,可以直接看到是 TF 问题还是消息类型不匹配。 - 确认消息类型。比如你的雷达消息是
sensor_msgs/LaserScan还是sensor_msgs/PointCloud2?如果在By topic里看到这个话题,但是双击却显示不支持,可能是消息类型对不上该插件。比如只有 PointCloud2 数据,但你想加 LaserScan 显示项,自然什么都出不来。 - 最后还有一个隐蔽问题:时间同步。如果 rosbag 回放时没有用
--clock,RVIZ 有时候会自动忽略延迟过大的数据。试着取消 RVIZ 顶部的Use sim time选项,或者重新播放 bag 时加--clock,再看。
7.4 插件缺失与界面显示空白
RVIZ 的架构是插件化的。你 Add 的时候如果找不到某种显示类型,比如找不到LaserScan,说明rviz包对应的插件没导入。排查:
rosdep check rviz如果提示缺依赖,就安装。还有一种场景:你更新了 ROS 之后,旧的插件缓存没清理,RVIZ 打开显示项时加载失败。解决办法:
rm -rf ~/.config/ros.org/rviz rm -rf ~/.rviz重新启动 RVIZ,它会生成默认配置。这个方法清掉的是 RVIZ 的缓存配置,不影响你的工程代码,可以放心用。
如果你自定义过 RVIZ 插件,比如给某个传感器做了专用显示插件,没把插件库路径加进环境变量也会找不到。通常做法是:
export ROS_PACKAGE_PATH=/path/to/your_plugin_pkg:$ROS_PACKAGE_PATH然后在Add面板的类型列表里看到你的插件。这个属于进阶操作,新手一般用不到,但知道原理后,下次看到类型列表里少东西就不会慌了。
我在实际项目里还遇到过一种“显示空白”的怪现象:RVIZ 能正常打开,但整个 3D 视图区一片灰色,左下角状态栏写着Noise或者一直转圈。这种多半是显卡驱动把 OpenGL 版本降到 1.x 导致部分渲染特性失效。检查可以在 RVIZ 里按Ctrl + I打开渲染信息,看看 OpenGL 版本。低于 2.0 的话,还是老老实实装回显卡驱动,或者调低渲染质量。
8. 一套顺手的配置方案(我的日常模板)
写到最后,分享一套我自己日常调车用的 RVIZ 模板配置,不是标准答案,但能帮你少走弯路。配置项:
Fixed Frame:odom- 显示项:Grid、TF、RobotModel、LaserScan、PointCloud2、Path
- Grid:平面高度
0,颜色默认偏灰,Cell Size1.0。导航调试时如果地面格子太密,我会调成2.0,看着清爽 - TF:
Marker Scale设为0.5,Show Names勾上 - LaserScan:
Size设0.03,Color设255 0 0,Decay Time设 0 - PointCloud2:
Size设0.02,Style设Points,Color Transformer设FlatColor,亮绿0 255 0 - Path:如果跑导航,把
Path话题加到/move_base/TebLocalPlannerROS/global_plan或/plan,线宽设0.05
这套模板在差速小车、阿克曼小车、机械臂项目里都适用。你可以在 RVIZ 里调好后,File → Save Config As存成my_debug.rviz,以后每次跑新项目第一件事就是:
rviz -d my_debug.rviz对 RVIZ 的掌握,本质上是一个“多动手、多把玩属性面板”的过程。很多人误以为这是很复杂的软件,其实它比 3D 建模软件简单得多,核心就是记住两件事:一是 Fixed Frame 决定全局坐标系,二是一切显示都靠左侧 Displays 面板驱动。把这两条内化之后,你再去看 TF 树、看 Topic 频率、看插件状态,都会变得顺理成章。
如果后面有条件,我打算再写一篇结合 Gazebo 仿真环境做完整机器人导航可视化的文章,把 RVIZ、Gazebo、move_base 串成一个完整的调试闭环。那样你会更直观地看到,这个工具在日常开发里能省下你多少时间。