基于 ROS2 与 TurtleBot3 的机器人全局路径规划、局部避障及轨迹跟踪控制优化

📅 2026/7/2 13:28:19
基于 ROS2 与 TurtleBot3 的机器人全局路径规划、局部避障及轨迹跟踪控制优化
一、基础环境准备1. 检查当前环境ctrlaltT打开新终端#检查检查 Ubuntu 系统版本 lsb_release -a #检查当前ros2环境变量 echo $ROS_DISTRO # 检查是否存在 ROS 1 的包应无输出或未安装 dpkg -l | grep ros-noetic-turtlebot3 # 检查当前已安装的 ROS 2 Humble 相关包 apt list --installed | grep ros-humble-turtlebot3 apt list --installed | grep ros-humble-nav2预期输出如下输出中的Description:应当显示Ubuntu 22.04.x LTS预期输出如下终端应直接输出humble根据最后三条指令的内容发给ai进行我们的环境安装包的安装完整安装了 ROS 2 Humble 版本的turtlebot3全系列包包括仿真环境turtlebot3-gazebo、键盘控制turtlebot3-teleop、甚至是用于后续导航的turtlebot3-navigation2需要补齐Nav2导航组件、TEB规划器以及建图算法工具箱的参考以下安装内容2. 核心安装包更新与一键配置一键安装缺失的 Nav2 导航核心及相关插件# 1. 更新本地系统软件源索引 sudo apt update # 2. 一键安装大作业所需的全部官方 ROS 2 核心导航、建图算法与稳定中间件剔除TEB # 在ROS 2 Humble中TEB算法虽然已被开源移植但它并没有被打包进官方的Ubuntu apt二进制源中 # 我们在步骤3中通过开源下载 sudo apt install -y \ ros-humble-navigation2 \ ros-humble-nav2-bringup \ ros-humble-slam-toolbox \ ros-humble-rmw-cyclonedds-cpp检查并配置.bashrc环境变量# 1. 确保刷新了 Humble 核心环境 echo source /opt/ros/humble/setup.bash ~/.bashrc # 2. 设置小车模型为 burger 汉堡包如果是 waffle_pi 请自行修改 echo export TURTLEBOT3_MODELburger ~/.bashrc # 3. 指定通信中间件为 CycloneDDS 确保数据吞吐稳定 echo export RMW_IMPLEMENTATIONrmw_cyclonedds_cpp ~/.bashrc # 4. 激活当前终端的环境变量 source ~/.bashrc3. 构建工作空间并安装TEB新建工作空间并进入mkdir -p ~/turtlebot3_ws/src cd ~/turtlebot3_ws/src下载以下三个源码的.zip文件并将其放到我们的~/turtlebot3_ws/src目录下GitHub - ROBOTIS-GIT/turtlebot3_simulations at humble · GitHubSimulations for TurtleBot3. Contribute to ROBOTIS-GIT/turtlebot3_simulations development by creating an account on GitHub.https://github.com/ROBOTIS-GIT/turtlebot3_simulations/tree/humbleGitHub - ROBOTIS-GIT/turtlebot3 at humble · GitHubROS packages for Turtlebot3. Contribute to ROBOTIS-GIT/turtlebot3 development by creating an account on GitHub.https://github.com/ROBOTIS-GIT/turtlebot3/tree/humbleGitHub - ros-navigation/navigation2_tutorials at humble · GitHubTutorial code referenced in https://docs.nav2.org/ - GitHub - ros-navigation/navigation2_tutorials at humblehttps://github.com/ros-navigation/navigation2_tutorials/tree/humble# 1. 解压官方 TEB 教程包并规范重命名 unzip navigation2_tutorials-humble.zip -d . mv navigation2_tutorials-humble navigation2_tutorials # 2. 解压 TurtleBot3 核心包并规范重命名 unzip turtlebot3-humble.zip -d . mv turtlebot3-humble turtlebot3 # 3. 解压 TurtleBot3 仿真包并规范重命名 unzip turtlebot3_simulations-humble.zip -d . mv turtlebot3_simulations-humble turtlebot3_simulations # 4. 清理掉已经解压完的 zip 包保持工作空间干净 rm *.zip # 5. ls检查检查目录结构 ls一键安装底层依赖并编译# 1. 回到工作空间的根目录 cd ~/turtlebot3_ws # 2. 更新本地 rosdep 数据库 rosdep update # 3. 一键自动安装 src 目录下所有源码包缺少的底层系统依赖 rosdep install --from-paths src --ignore-src -r -y # 4. 一键编译确保在 ~/turtlebot3_ws 目录下执行编译命令 colcon build刷新并永久化工作空间环境# 将工作空间的刷新脚本写入环境 echo source ~/turtlebot3_ws/install/setup.bash ~/.bashrc # 让其在当前终端立即生效 source ~/.bashrc二、Gazebo 仿真、扫图与建图 (SLAM)1. 启动 Gazebo 物理仿真迷宫世界打开一个新的终端执行以下指令打开我们的世界export TURTLEBOT3_MODELburger ros2 launch turtlebot3_gazebo turtlebot3_world.launch.py2. 启动 SLAM 异步建图工具箱打开一个新的终端执行以下指令启动建图算法节点执行打开rviz2export TURTLEBOT3_MODELburger ros2 launch slam_toolbox online_async_launch.py use_sim_time:True3. 启动 Rviz2打开一个新的终端执行以下指令启动建图算法节点执行打开rviz2点击右下方的add按钮export TURTLEBOT3_MODELburger ros2 launch turtlebot3_bringup rviz2.launch.py rviz_config:/home/a/turtlebot3_ws/src/turtlebot3/turtlebot3_bringup/rviz/turtlebot3_slam.rviz选择我们的map并点击OK将其添加到我们的左侧栏里展开我们的map并在对应的topic栏选择map此时我们的地图显示成功进入下一步4. 启动键盘遥控节点开始扫图打开一个新的终端执行以下指令开始构建我们的地图export TURTLEBOT3_MODELburger ros2 run turtlebot3_teleop teleop_keyboard扫图操作将鼠标指针保持点击在终端4窗口内部使用键盘上的w前进、a左转、s后退、d右转、x刹车/停止 来控制小车眼睛看着 Rviz2终端 2 的界面控制小车缓缓地在迷宫里兜圈子把原本灰色的“未知区域”全部“刮”成白色直到障碍物的黑色轮廓完整连成一片5. 保存地图打开一个新的终端执行以下指令保存我们构建的地图mkdir -p ~/turtlebot3_ws/src/my_map ros2 run nav2_map_server map_saver_cli -f ~/turtlebot3_ws/src/my_map/map --fmt png执行以上命令后我们在src目录下创建my_map文件夹会显示我们刚刚保存的地图关闭我们刚刚建图打开的所有终端三、开启自主导航实战1. 启动 Gazebo 物理仿真世界打开一个新的终端导航需要物理世界提供真实的激光雷达和里程计数据所以执行以下指令打开我们的世界export TURTLEBOT3_MODELburger ros2 launch turtlebot3_gazebo turtlebot3_world.launch.py2. 修改我们的配置文件burger.yaml修改并保存参数在编辑器中改完你想要的参数比如把use_astar改成true或者调整了sim_time按下Ctrl S保存文件# 用 VS Code 打开 code /home/a/turtlebot3_ws/src/turtlebot3/turtlebot3_navigation2/param/burger.yaml按照以下表格内容分别对我们的数据进行修改每次只修改一个实验组对应的参数其他参数全部恢复成默认值。测试完并记录数据后再把这个参数改回去接着测下一个执行完步骤n后回到该步骤修改参数继续顺序执行3.1 全局路径规划对比实验参数Dijkstra vs A*实验组别核心参数名称默认值 / 基准值实验修改值参数物理意义与实验观察点Dijkstra 组use_astarfalse保持false此时使用 Dijkstra 算法全图盲目搜索计算时间较长路径几何最优。A* 组use_astarfalse修改为true开启 A* 启发式搜索。对比观察终端日志中的计算时间Time是否暴跌。敏感度调节组 Aneutral_cost50调大至120或者调小至10网格底色代价。数值越大算法越倾向于走直线数值越小路径越容易产生细微折线。敏感度调节组 Bcost_factor3.0调大至5.0代价因子。调大后小车规划的路径会刻意远离圆柱体等障碍物走空旷地带。所属节点名称Ctrl F 搜索planner_server表二局部路径规划与控制特性参数DWA 控制器实验内容大纲对应参数名称默认值 / 基准值实验修改建议值参数物理机理与实验报告分析点3.2 局部规划激进速度流max_vel_xgoal_distance_bias0.2224.0调大至0.30调大至40.0小车最高线速度变快且更渴望直奔终点。观察其在圆柱体阵列中是否容易刹车不及、速度产生剧烈震荡。3.2 局部规划保守贴线流path_distance_biasoccdist_scale32.00.02调大至60.0调大至0.10强化贴合全局路径的惩罚。小车会死死咬住中线在障碍物前极度小心、频繁扭捏微调。3.3 轨迹控制直道响应速度max_vel_theta2.8调大至4.0或者调小至1.5最大角速度。数值越大偏离直道后修正车头的响应速度越快误差曲线收敛越陡峭。3.3 轨迹控制稳态误差控制path_distance_bias32.0暴增至100.0路径跟踪权重。数值极高时稳态误差极小但由于惯性容易在直道两侧来回“画龙”蛇形震荡。3.3 轨迹控制U型弯前视时间sim_time1.5极限缩短至0.5近视眼效应走一步看一步。过弯动作生硬频繁打方向和减速但在窄道内贴边紧。3.3 轨迹控制U型弯前视时间sim_time1.5大幅延长至2.5远视眼效应类比大前视距离。过弯圆弧极顺滑但无法感知眼前的急弯入弯过早切内圈导致直接撞墙。所属节点名称Ctrl F 搜索controller_server表三局部路径规划算法彻底切换DWA ↔ TEB算法模式需要修改的参数项名默认值DWA切换修改值TEB综合对比观察点走廊/死胡同/密集障碍物切换为 TEB 算法plugindwb_core::DWBLocalPlannernav2_teb_controller/TebLocalPlanner(注以你实际编译出的插件名为准)1. 死胡同场景DWA 无法倒车卡死TEB 能够弹性倒车脱困。2. 速度平滑度TEB 过弯呈平滑圆弧DWA 呈生硬折线且速度频繁震荡。当你做完 DWA 所有的调参进入 “DWA 与 TEB 综合对比” 环节时你需要修改控制器的核心插件声明所属节点名称Ctrl F 搜索controller_server中的FollowPath3. 启动 Nav2 导航堆栈打开一个新的终端所以执行以下指令启动定位算法AMCL、地图服务器Map Server和路径规划器export TURTLEBOT3_MODELburger ros2 launch turtlebot3_navigation2 navigation2.launch.py use_sim_time:True map:/home/a/turtlebot3_ws/src/my_map/map.yaml此时我们rviz打开后我们的小车没有找到自己的位置左侧的导航状态目前是unknown未知4. 在地图上对小车进行定位先对小车进行定位在 Rviz2 顶部的工具栏中点击2D Pose Estimate按钮观察 Gazebo 中小车的位置默认在中心在 Rviz2 地图的中心对应的位置按住鼠标左键不放顺着小车车头的朝向拉出一个绿色的箭头然后松开此时小车周围散落的绿色粒子群会瞬间聚拢红色雷达点会和地图的黑色墙壁完美重合此时我们还可以打开一个新的终端并执行以下指令来确定我们的雷达和地图对齐即定位是否精准ros2 topic echo /amcl_pose --field pose.covariance方向方差第1个值代表小车在横向位置上的不确定度方向方差第7个值代表小车在纵向位置上的不确定度。朝向角方差第36个值即最后一个值代表车头角度的不确定度。对齐良好的标准这些数值应该非常接近 0通常在0.001到0.01数量级。如果数值很大比如超过0.5说明小车自己都“不知道自己在哪”雷达必然没有对齐5. 算法的导航验证下发导航目标点击 Rviz2 顶部工具栏的Nav2 Goal按钮图标通常是一个带有绿色箭头的靶心在地图上选择一个距离小车较远、且中间隔着几个圆柱体障碍物的空白区域最好是对角线点击鼠标左键并拖拽出一个箭头箭头方向代表小车到达终点后的车头朝向后松开。注意我们每一次实验的起点和终点要相同你会看到地图上瞬间生成了一条从当前位置到终点的粉色平滑长线条。观察算法的表现记录实验数据在机器人接收到导航目标Nav2 Goal并开始自主移动后保持 Rviz2 可视化界面与控制终端终端 2前台运行。不进行任何人工干预通过拦截系统的底层日志时间戳提取关键量化指标拦截全局规划耗时读取日志中bt_navigator启动时间戳与controller_server首次计算控制量的时间戳两者的绝对差值即为全局规划算法Dijkstra/A*的纯计算响应时间。统计局部重规划频次统计全程日志输出Passing new path to controller的总次数用以量化评估局部规划器对全局轨迹的跟踪敏感度与刷新频率。计算绝对导航总耗时在终端打印出Reached the goal!时拦截该行时间戳并与启动时间戳相减计算出机器人从起点到终点的实际运行总时间。定性观察速度动态波动在机器人通过密集障碍物等瓶颈路段时实时监听/cmd_vel话题记录角速度angular.z在正负号之间的跳变频率作为评估算法控制平滑度与速度震荡的依据。在工作空间中创建并编写文件打开终端直接利用绝对路径在 TurtleBot3 源码路径下新建并打开文件gedit /home/a/turtlebot3_ws/src/turtlebot3/turtlebot3_navigation2/vel_oscillation_node.py复制以下代码#!/usr/bin/env python3 import rclpy from rclpy.node import Node from geometry_msgs.msg import Twist import time class VelOscillationPlanner(Node): def __init__(self): super().__init__(vel_oscillation_planner) # 订阅 /cmd_vel 话题 self.subscription self.create_subscription( Twist, /cmd_vel, self.cmd_vel_callback, 10 ) # 核心统计变量 self.last_sign 0 # 记录上一次角速度的正负号 (1代表正, -1代表负, 0代表静止) self.jump_count 0 # 跳变次数计数器 self.start_time None # 导航开始时间 self.get_logger().info( 速度震荡与控制抖动实时监听节点已启动...) self.get_logger().info(正在等待小车运行并发布 /cmd_vel 数据...\n) def cmd_vel_callback(self, msg): current_w msg.angular.z current_time time.time() # 只有当小车真正开始运动时才初始化启动时间 if self.start_time is None and (abs(msg.linear.x) 0.001 or abs(current_w) 0.001): self.start_time current_time self.get_logger().info(⏱️ 检测到小车启动开始统计跳变频率...) # 确定当前速度符号 if current_w 0.005: current_sign 1 # 左转 elif current_w -0.005: current_sign -1 # 右转 else: current_sign 0 # 保持直行 # 核心逻辑判断符号是否发生穿零跳变从左打方向突变为右打方向或反之 if self.last_sign ! 0 and current_sign ! 0 and current_sign ! self.last_sign: self.jump_count 1 # 计算从启动到现在的平均跳变频率 (次/秒) duration current_time - self.start_time frequency self.jump_count / duration if duration 0 else 0.0 # 终端高亮实时打印 print(f⚠️ [检测到震荡] 当前角速度: {current_w:6.3f} | 总跳变次数: {self.jump_count:3d} | 平均频率: {frequency:5.2f} Hz) # 更新状态留待下一帧对比 if current_sign ! 0: self.last_sign current_sign def main(argsNone): rclpy.init(argsargs) node VelOscillationPlanner() try: rclpy.spin(node) except KeyboardInterrupt: print(\n 监听结束。) finally: node.destroy_node() rclpy.shutdown() if __name__ __main__: main()赋予脚本执行权限由于是在src源码目录内新建的脚本Linux 系统默认不给予其执行权限。你必须在终端中运行以下命令将其变成可执行文件chmod x /home/a/turtlebot3_ws/src/turtlebot3/turtlebot3_navigation2/vel_oscillation_node.py在实验中快捷运行在 Rviz2 中点击Nav2 Goal下发了导航目标小车开始在仿真环境里自主移动时立刻新建一个终端 3直接通过路径运行这个脚本python3 /home/a/turtlebot3_ws/src/turtlebot3/turtlebot3_navigation2/vel_oscillation_node.py保存可视化状态凭证系统提示Goal succeeded后对 Rviz2 界面进行全屏截图记录全局路径几何形态、局部代价地图膨胀层与静态地图的贴合情况作为轨迹跟踪特性的直观物证。