教程七 cartographer建图教程

来自Waveshare Wiki
跳转至: 导航搜索

ugv02使用教程

功能包简介

Cartographer是一个开源的SLAM(Simultaneous Localization and Mapping)库,用于在机器人或移动设备上进行实时建图和定位。它由Google开发并在ROS(Robot Operating System)中得到广泛应用。

Cartographer使用多个传感器(如激光雷达、惯性测量单元和相机)来获取环境的感知数据,并通过SLAM算法将这些数据融合在一起,实现同时定位和建图。它能够在未知环境中实时生成高质量的地图,并提供准确的机器人定位信息。

例程

安装cartographer

使用apt安装cartographer

sudo apt install ros-humble-cartographer
sudo apt install ros-humble-cartographer-ros

检查安装情况

ros2 pkg list | grep cartographer

输出下面字样则表示安装成功

cartographer_ros
cartographer_ros_msgs

创建功能包

进入工作空间

cd */ugv02/src

创建功能包

ros2 pkg create ugv02_cartographer

创建launch、config文件夹

cd ugv02_cartographer
mkdir config launch

编写cartographer建图配置

在ugv02_cartographer/config目录下创建建图配置文件cartographer_2d.lua文件。

include "map_builder.lua"  
include "trajectory_builder.lua"  

options = {
  map_builder = MAP_BUILDER,  
  trajectory_builder = TRAJECTORY_BUILDER,  
  map_frame = "map",  -- 地图帧的名称
  tracking_frame = "laser_link",  -- 跟踪帧的名称
  published_frame = "base_link",  -- 发布帧的名称
  odom_frame = "odom",  -- 里程计帧的名称
  provide_odom_frame = true,  -- 是否提供里程计帧
  publish_frame_projected_to_2d = false,  -- 是否发布2d姿态
  use_pose_extrapolator = false,
  use_odometry = false,  -- 是否使用里程计
  use_nav_sat = false,  -- 是否使用导航卫星
  use_landmarks = false,  -- 是否使用地标
  num_laser_scans = 1,  -- 激光雷达的数量
  num_multi_echo_laser_scans = 0,  -- 多回波激光雷达的数量
  num_subdivisions_per_laser_scan = 1,  -- 每个激光扫描的细分数量
  num_point_clouds = 0,  -- 点云的数量
  lookup_transform_timeout_sec = 0.2,  -- 查找变换的超时时间(秒)
  submap_publish_period_sec = 0.3,  -- 子地图发布周期(秒)
  pose_publish_period_sec = 5e-3,  -- 姿态发布周期(秒)
  trajectory_publish_period_sec = 30e-3,  -- 轨迹发布周期(秒)
  rangefinder_sampling_ratio = 1.,  -- 测距仪采样比率
  odometry_sampling_ratio = 1.,  -- 里程计采样比率
  fixed_frame_pose_sampling_ratio = 1.,  -- 固定帧姿态采样比率
  imu_sampling_ratio = 1.,  -- IMU采样比率
  landmarks_sampling_ratio = 1.,  -- 地标采样比率
}
 
MAP_BUILDER.use_trajectory_builder_2d = true  -- 是否启动2D SLAM
TRAJECTORY_BUILDER_2D.submaps.num_range_data = 35  -- 2D轨迹构建器中子地图的范围数据数量
TRAJECTORY_BUILDER_2D.min_range = 0.1  -- 限制在雷达最小扫描范围,比机器人半径小的都忽略
TRAJECTORY_BUILDER_2D.max_range = 3.5  -- 限制在雷达最大扫描范围
TRAJECTORY_BUILDER_2D.missing_data_ray_length = 5.  -- 限制在雷达最大扫描范围
TRAJECTORY_BUILDER_2D.use_imu_data = false  -- 是否使用IMU数据
TRAJECTORY_BUILDER_2D.use_online_correlative_scan_matching = true  -- 是否使用实时回环检测扫描匹配

TRAJECTORY_BUILDER_2D.motion_filter.max_angle_radians = math.rad(0.1)  -- 1.0改成0.1,提高对运动的敏感度
POSE_GRAPH.constraint_builder.min_score = 0.65  -- 0.55改成0.65,Fast csm的最低分数,高于此分数才进行优化。
POSE_GRAPH.constraint_builder.global_localization_min_score = 0.7  --0.6改成0.7,全局定位最小分数,低于此分数则认为目前全局定位不准确

return options


在路径src/ugv02_cartographer/launch/下新建cartographer.launch.py文件,接下来将开始编写启动cartographer建图节点的launch文件。

import os
from launch import LaunchDescription
from launch.substitutions import LaunchConfiguration
from launch_ros.actions import Node
from launch_ros.substitutions import FindPackageShare

def generate_launch_description():
    # 定位功能包
    pkg_share = FindPackageShare(package='ugv02_cartographer').find('ugv02_cartographer')
    
    #配置节点启动信息
    use_sim_time = LaunchConfiguration('use_sim_time', default='true')
    # 地图的分辨率
    resolution = LaunchConfiguration('resolution', default='0.05')
    # 地图的发布周期
    publish_period_sec = LaunchConfiguration('publish_period_sec', default='1.0')
    # 配置文件夹路径
    configuration_directory = LaunchConfiguration('configuration_directory',default= os.path.join(pkg_share, 'config') )
    # 配置文件
    configuration_basename = LaunchConfiguration('configuration_basename', default='cartographer_2d.lua')

    #声明节点
    cartographer_node = Node(
        package='cartographer_ros',
        executable='cartographer_node',
        name='cartographer_node',
        output='screen',
        parameters=[{'use_sim_time': use_sim_time}],
        arguments=['-configuration_directory', configuration_directory,
                   '-configuration_basename', configuration_basename])

    cartographer_occupancy_grid_node = Node(
        package='cartographer_ros',
        executable='cartographer_occupancy_grid_node',
        name='cartographer_occupancy_grid_node',
        output='screen',
        parameters=[{'use_sim_time': use_sim_time}],
        arguments=['-resolution', resolution, '-publish_period_sec', publish_period_sec])

    #启动文件
    ld = LaunchDescription()
    ld.add_action(cartographer_node)
    ld.add_action(cartographer_occupancy_grid_node)

    return ld


打开src/ugv02_cartographer/CmakeLists.txt,添加安装指令,使编译后系统能找到这些文件。

install(
  DIRECTORY config launch
  DESTINATION share/${PROJECT_NAME}
)

编译

返回工作空间并编译

cd ~/ugv02
colcon build

运行测试

新开一个终端页面,进入工作空间,source一下,以及启动*教程五 ugv02使用雷达教程中的雷达(确保串口已授权)

cd ~/ugv02
source ./install/setup.bash
ros2 launch ldlidar_stl_ros2 ld19.launch.py

新开一个终端页面,进入工作空间,source一下,以及启动建图

cd ~/ugv02
source ./install/setup.bash
ros2 launch ugv02_cartographer cartographer.launch.py

在装有ubuntu系统及ros2的电脑(虚拟机)中,确保该电脑与树莓派连接了同一个网络或wifi,新开一个终端。

rviz2

点击rviz左下角的add按钮,在rviz中添加控件以显示地图
Rviz添加控件显示地图.png

地图效果如下
Rviz地图显示效果.png
接下来你可以按照*教程五 ugv02使用雷达教程在rviz中添加雷达点云数据显示及车辆坐标系,接着参照*教程三 底盘控制教程控制小车移动,观察建图效果和过程。
当你觉得图建的差不多的时候,使用以下命令保存地图。
先安装地图管理功能包。

sudo apt install ros-humble-nav2-map-server

运行地图保存命令最后一个参数为地图路径及名字。

ros2 run nav2_map_server map_saver_cli -f ./map