实机开导航,RViz 收不到地图数据?


实机开 Nav2,Rviz 的 Map 经常出现 No map received、整屏灰、或 Fixed Frame 报错。下面按出现频率把原因拆开,并给出对应命令和改法。

范围说明:

  • 导航:静态地图由 map_server 发 /map
  • SLAM 建图:/map 多半来自 Cartographer 的 occupancy grid 节点、或 slam_toolbox,不是 map_server
  • 局部代价地图、激光显示本身、全局路径不在此列;但 /scan、TF、时间源会直接影响 /map 能不能出来

适用说明

项 说明
文档类型 导航 / 建图联调 · 踩坑排查
适用场景 实机 / 仿真导航;SLAM 建图;本机或远程 Rviz
实测软件 Ubuntu 22.04 · ROS 2 Humble · Nav2 · Rviz2
参考工程 ROSLander / MentorPi 等 navigation + map_server 栈;FishBot Cartographer 一类教程

1. 现象与定位范围

常见情况:

  • Map 状态:No map received / No tf data
  • ros2 topic list 里有 /map,Rviz 仍空白
  • 车上 echo 有数据,远程 PC 的 Rviz 没有
  • Costmap 能看见,静态地图没有(或反过来)
  • 只起了建图 launch,没有底盘 / 仿真 / 雷达,节点很少,/map 一直不出现

先分清你在查哪一种:

场景 /map 通常谁发 还依赖什么
导航加载已有地图 map_server yaml/pgm、lifecycle、TF
SLAM 在线建图 cartographer_occupancy_grid / slam_toolbox 等 /scan(或深度)、里程计、完整 TF、时间源一致

不要把 costmap、点云和 /map 混在同一症状里一起改。


2. 地图数据怎么到 Rviz

导航(map_server) 正常时大致如下:

环节 正常时应有
地图文件 xxx.yaml + xxx.pgm,路径真实存在
map_server lifecycle 为 active
话题 /map(或 /robot_x/map),类型 nav_msgs/msg/OccupancyGrid
QoS 多为 Reliable + Transient Local
Rviz Fixed Frame 为 map;Map 插件 Topic 对上

SLAM 建图时,链路变成:雷达/里程计 → SLAM 节点 →(occupancy grid)→ /map。任一上游断了,Rviz 都会表现为 map 缺失。鱼香 ROS 教程里 Cartographer 建图出问题,很多其实不是 “lua 文件名写错”,而是 传感器、TF、时间源或启动组合不完整。

和 /scan 不同:导航阶段的 /map 往往不是持续高频流,而是发完靠 Transient Local 留给后来的订阅者。用 ros2 topic hz 去听频率,容易误判。建图阶段 /map 会随探索更新,但仍要先保证有第一帧。


3. 常见根因对照

按实机 / 教程联调里更常见的顺序:

优先级 根因 典型线索 怎么处理
1 发布端没起来(map_server 或 SLAM/occupancy_grid) 无对应节点;lifecycle 非 active;只起了建图 launch 查 launch 组合、lifecycle、地图路径
2 上游数据断了(/scan、odom、TF) 有 SLAM 节点但无 /map;Message Filter dropping;无 map→odom 查雷达、里程计、TF 树
3 时间源不一致(use_sim_time / 多机时钟) 仿真混用、树莓派与 PC 差几秒;TF 树跑着跑着断 统一 sim_time;多机做 NTP
4 话题名 / 命名空间不一致 车上 /robot_1/map,Rviz 订 /map Topic 和 Fixed Frame 一起改
5 QoS 不匹配,晚加入拿不到历史 list 有话题,默认 echo 卡住或为空 Transient Local + Reliable 再 echo
6 Fixed Frame / Rviz 配置 Fixed Frame 下拉里没有 map;Map 未勾选 先修 TF,再设 Fixed Frame
7 跨机 Domain / 网络 本机有图,远程没有 对齐 ROS_DOMAIN_ID、网段

建议从上往下查。教程帖里常见误判:配置文件名已经对上,却一直在改 .lua,忽略了 launch 是否带齐底盘与雷达。


4. 排查步骤

在跑导航 / 建图的机器上执行(远程 Rviz 先保证 Domain 与网络一致)。

4.1 命令快检

# 1) 节点:导航看 map_server;建图看 cartographer / slam_toolbox
ros2 node list | grep -E 'map_server|amcl|cartographer|slam_toolbox|occupancy_grid'

# 2) 话题
ros2 topic list | grep -E 'map|scan|odom'
ros2 topic info /map -v          # 有命名空间则改实际名
ros2 topic hz /scan              # 建图场景必查

# 3) 能否收到一帧地图(指定 QoS,避免默认策略误判)
ros2 topic echo /map --once --qos-durability transient_local --qos-reliability reliable

# 4) TF
ros2 run tf2_ros tf2_echo map odom
ros2 run tf2_tools view_frames
# 或:ros2 run rqt_tf_tree rqt_tf_tree

# 5) 时间源(仿真 / 多机)
ros2 topic echo /clock --once    # 若用仿真时间,应有 /clock
echo $ROS_DOMAIN_ID

4.2 结果怎么对应

快检结果 优先查
无 map_server / 无 SLAM 相关节点 launch 是否启动完整;lifecycle
有 SLAM 节点、无 /map,且 /scan 无频率 雷达驱动、串口、是否被别的 launch 抢设备
/scan 正常,无 map→odom TF、里程计、SLAM 是否真正在跑
仿真下 TF 乱、消息被 drop use_sim_time 是否全局一致
树莓派建图、PC 上看 map/TF 异常 两端 NTP 时间同步
topic info 有 Publisher,默认 echo 空,加 Transient Local 才有 QoS
echo 有数据,Rviz 仍空 见第 5 节:Topic / Fixed Frame / Rviz QoS
本机有,远程无 Domain / 网络

4.3 再看 Rviz 面板(速览)

详细面板操作见下一节。这里先记四条:

  1. Fixed Frame 是否为 map
  2. Map 的 Topic 是否与实际发布一致
  3. Map 是否勾选;可取消再勾选一次重订阅
  4. 状态是 No map received 还是 No tf data——两种修法不同

5. Rviz 收不到 map:订阅端怎么查

命令行已经能 echo /map 出数据,但 Rviz 仍空白时,问题多半在 Rviz 这一侧的订阅与坐标系,而不是 map_server 没发。

5.1 先分清两种报错

点开 Displays 里 Map 左侧的状态(或看窗口左下角 Global Status):

状态文案 含义 先查什么
No map received Map 显示没订到 OccupancyGrid Topic 名、QoS、发布端是否真有数据、Rviz 是否晚加入
No tf data / Fixed Frame 报错 有图也可能画不出,或帧根本不存在 Fixed Frame、map→odom→base、AMCL / SLAM 是否在发 TF
Topic 为空 / Error subscribing 显示项 Topic 没填或填错 手动填 /map 或实际命名空间话题
OK 但仍看不见 数据到了,显示参数把图“藏”了 Alpha、Color Scheme、视角、高度裁剪

ros2 topic echo 成功只说明 DDS 上有人在发、当前终端订得到。Rviz 是另一个订阅者,Topic、QoS、Fixed Frame 任一不对,照样 No map received。

5.2 确认 Rviz 是否真的订上了 /map

# 看 /map 当前有哪些订阅者(应出现 rviz 相关)
ros2 topic info /map -v
  • Publishers 为空:不是 Rviz 的问题,回到第 4 节查发布端
  • 有 Publisher、没有 Rviz 订阅:Map 显示未加、未勾选,或 Topic 写错导致没订上
  • 有 Rviz 订阅仍无图:优先查 Fixed Frame / TF,或 QoS 兼容后仍未拿到历史帧

也可在 Rviz 里:Add → By topic → 选 /map(类型 OccupancyGrid)→ Map,避免手填拼错。

5.3 Map 显示项逐项核对

项 建议
Topic 与 ros2 topic list 一致,如 /map 或 /robot_1/map
Reliability 与发布端一致,一般为 Reliable
Durability 尽量 Transient Local(对应 map_server 晚加入仍能拿到最后一帧)
History / Depth 保持默认即可;Depth 过小一般不是主因
Alpha 不要为 0
Draw Behind / 高度 误调可能导致“像没图”

操作顺序建议:

  1. Global Options → Fixed Frame = map
  2. 添加或勾选 Map,Topic 选对
  3. 若仍无图:取消勾选 Map → 再勾选(强制重新订阅)
  4. 仍无图:先开着 Rviz,再重启一次 map_server / 建图节点

5.4 Fixed Frame 与“有数据却不画”

Rviz 画 OccupancyGrid 要用 Fixed Frame 做坐标变换。常见情况:

  • Fixed Frame 还是 odom / base_link:地图在 map 下,变换不对时可能空白或位置错乱
  • Fixed Frame 下拉里 没有任何帧:说明几乎没收到 TF,先查底盘 / SLAM,不是改 Map Topic 能解决的
  • 有 /map、无 map→odom:导航时 AMCL 未定位,或建图时 SLAM 尚未产出 map 帧
ros2 run tf2_ros tf2_echo map odom
ros2 run tf2_tools view_frames

5.5 本机 echo 有、Rviz 无:快速对照

检查 命令 / 操作 期望
话题有数据 ros2 topic echo /map --once --qos-durability transient_local --qos-reliability reliable 打出一帧
Rviz 已订阅 ros2 topic info /map -v 订阅者含 rviz
Fixed Frame Rviz Global Options map
Map Topic Displays → Map 与发布名一致
重订阅 取消/勾选 Map,或先 Rviz 后 map_server 图出现

到这里仍没有图,再查跨机 Domain、Docker 网络(第 7 节),或发布端是否只对部分订阅者可见。


6. 按根因处理

6.1 发布端未就绪(导航 map_server)

常见情况:localization 没随导航起来;yaml 路径空或错;lifecycle 停在 unconfigured / inactive。

ls -l ~/ros2_ws/src/slam/maps/map_01.yaml
# yaml 里 image 指向的 pgm 也要在

ros2 lifecycle get /map_server
ros2 lifecycle set /map_server configure
ros2 lifecycle set /map_server activate

ROSLander 一类工程里,map:= 必须以 launch 传入为准;nav2_params.yaml 里的 yaml_filename 常被 RewrittenYaml 覆盖。

6.2 SLAM 建图时 /map 出不来

教程里只跑 cartographer.launch.py、却忘了先起仿真 / 实车 bringup(雷达、里程计、robot_state_publisher)时,节点列表会明显偏少,后面再怎么对 .lua 文件名也出不了图。

建议对照:

  1. 先起底盘 / Gazebo / 雷达相关 launch,确认 /scan、/tf 正常
  2. 再起建图 launch
  3. ros2 node list 里应能看到 Cartographer(或 slam_toolbox)以及生成栅格图的相关节点
  4. 日志里若出现 Message Filter dropping message、queue is full,优先查 TF 时间戳 和 激光 frame 是否对上

在线建图阶段不要指望 map_server;那是保存地图之后、导航加载静态图才用的。

6.3 /scan、odom、TF 上游断开

ros2 topic hz /scan
ros2 topic echo /tf --once
ros2 run tf2_ros tf2_echo map odom
  • /scan 都没有:先修雷达驱动、设备权限、launch 是否重复占用串口
  • 有 scan、无 map→odom:SLAM 没建立起定位,或里程计 / 静态 TF 缺失
  • 实机常用 static_transform_publisher 补 base_link → laser;缺这段时,建图节点会持续丢激光

6.4 use_sim_time 与多机时间同步

环境 注意
纯仿真 相关节点统一 use_sim_time:=true,并有 /clock
纯实机 统一 use_sim_time:=false,不要残留仿真参数
树莓派建图 + PC 开 Rviz 两端用 NTP 对齐系统时间;差几秒就会导致 TF 树异常、map 显示不出来

鱼香 ROS 实车联调里,虚拟机与树莓派做完 NTP 后 TF / 建图恢复正常,是高频案例。不要只改 Rviz。

6.5 命名空间 / 话题不一致

ros2 topic list | grep -i map

实机开了命名空间后,话题可能是 /robot_1/map。Rviz 的 Map Topic 和 Fixed Frame 要一起改,只改其中一个仍会空白。

6.6 QoS

导航 map_server 常见策略是 Reliable + Transient Local。命令行默认多为 Volatile,晚加入时 echo 可能卡住或为空。

ros2 topic echo /map --once \
  --qos-reliability reliable \
  --qos-durability transient_local

自写订阅不要用 qos_profile_sensor_data 去订 /map。Nav2 / AMCL 侧常见:map_subscribe_transient_local: true。Rviz 里也可核对 Map 显示的 Reliability / Durability。

仍无图时:先开 Rviz,再启动 map_server;或对 Map 显示取消勾选再勾选,让它重新订阅历史帧。

6.7 Fixed Frame / TF

  1. Fixed Frame 先设为 map
  2. view_frames 确认是否有 map → odom → base_footprint
  3. 导航场景还要查 AMCL 是否 active、是否用 2D Pose Estimate 设过初始位姿

有 OccupancyGrid、没有合法 TF 时,Rviz 同样不画图。

6.8 地图文件损坏或路径错误(仅导航加载)

cat your_map.yaml
# image 相对路径相对 yaml 所在目录

只拷 yaml 忘了 pgm,或仿真路径原样搬到实机,都会卡在 map_server。


7. 跨机、Docker、命名空间

7.1 远程 PC 开 Rviz

echo $ROS_DOMAIN_ID
# 需要时可:export ROS_DOMAIN_ID=0

同一网段、DDS 能互相发现。WiFi 客户端隔离、VPN、虚拟机桥接失败时,常见是 topic list 偶发有、数据没有。远程先:

ros2 topic list
ros2 topic echo /map --once --qos-durability transient_local --qos-reliability reliable

远程 echo 都没有,先修网络 / Domain / 时间同步,再开 Rviz。

7.2 Docker 里跑导航 / 建图

确认网络模式(本机 Rviz 多用 host)、地图与配置目录是否挂进容器、容器内路径是否与 map:= 一致。远程连容器时优先查 Domain 和网络。

7.3 不要把 Costmap 当成 /map

话题 含义
/map 静态地图或 SLAM 栅格输出
/global_costmap/costmap 全局代价地图
/local_costmap/costmap 局部代价地图

只能看到 costmap、看不到静态 / SLAM 图,说明 /map 这条链还有问题。


8. 踩坑速查

现象 原因 处理
只起建图 launch,无 /map 缺雷达 / 底盘 / 仿真 先 bringup,再 SLAM
/scan 无数据 驱动、串口、设备占用 单独测雷达再并 launch
有节点、默认 echo /map 为空 Volatile 晚加入 加 Transient Local;或先开 Rviz 再起 map_server
有 OccupancyGrid,Rviz 仍 No map received Topic / QoS / 未勾选 Map 见第 5 节;topic info -v 确认 rviz 已订阅
有 OccupancyGrid,Rviz 灰或 No tf Fixed Frame / TF Fixed Frame 设为 map,查 TF
echo 有、Rviz 无 晚加入未拿到历史帧 先开 Rviz 再起 map_server;或重勾选 Map
仿真混用实机参数 use_sim_time 不一致 全栈统一 true 或 false
树莓派 + PC 联调 TF 乱 系统时间差 NTP 同步后再建图
仿真正常、实机不行 路径 / 命名空间 / Domain 核对 launch 与网段
改了 yaml 无变化 launch 覆盖了路径 查 RewrittenYaml / map:=
一直改 .lua 文件名仍无图 实际是上游数据或 TF 用 4.1 快检定位,不要只盯配置文件名