赞
踩
这套仿真环境是基于Ubuntu20.04环境下的ROS1+PX4固件的联合仿真,由于初次接触这方面的仿真环境搭建,几番寻找找到了国内的XTdrone开源无人机仿真平台,跟着这套仿真平台搭建了一个完整的仿真环境,XTdrone这个平台的简介可以参考这个视频:
XTDrone: 基于PX4、ROS和Gazebo的无人机通用仿真平台简介_哔哩哔哩_bilibili
这里再附上XTdrone的gitee链接 :
XTDrone: 基于PX4、ROS和Gazebo的无人机通用仿真平台
对于无人机仿真来说其实本质需要的就是三大部分,ROS环境,MAVROS包,PX4编译环境,ROS提供通讯和Gazebo仿真环境,PX4固件支持linux编译运行,并通过Gazebo仿真出来,还可连接QGC地面站,MAVROS则是ROS和PX4通讯的桥梁,因为PX4只支持mavlink通讯协议,而ROS则是基于话题,服务等通讯机制,所以需要有一个功能包去把话题和服务转换成mavlink协议,这个功能包就是MAVROS。
XTdrone的搭建有两个版本,一个是基于Ubuntu18.04的但由于Ubuntu18.04已经停止维护,所以更推荐基于Ubuntu20.04的版本,其对应的PX4版本也比较新。下面是搭建的官方教程,最好需要有科学上网的环境,不然配置起来很麻烦,另外官方的教程基于Ubuntu20.04可能安装的人并不多,所以坑还是不少的,每个人的坑也不太一样,不过这些坑基本可以从CSDN上找到解决办法。
此处为语雀内容卡片,点击链接查看:仿真平台基础配置(对应PX4 1.13版) · 语雀
当可以运行键盘控制无人机飞行则表明环境搭建成功
对于上层控制PX4,飞控端的模式是OFFBOARD,在这个模式下,可以通过mavlink协议,对无人机发送期望位置,期望速度,期望加速度来控制无人机,同时可以通过接收mavlink消息来获取无人机当前姿态。下面这个视频系列对这个模式有详细的介绍:
新手入门无人机+PX4+ROS工程应用开发?看这门课就够了 4.无人机offboard控制_哔哩哔哩_bilibili
同时介绍一下mavros功能包,这个功能包所包含的话题和服务种类很多,这里列举几个常用的消息话题:
【精选】ROS系列——mavros功能包中常用话题和服务介绍,包括消息名称、类型、头文件、成员变量、示例代码_mavros/mission/waypoint-CSDN博客
常用的基本上也就是以下这几个
第一步需要启动PX4官方的一个仿真launch文件
cd ~/PX4_Firmware roslaunch px4 mavros_posix_sitl.launch
此时会启动一个Gazebo的仿真环境,如下图所示
再新开一个终端,并运行
rostopic echo /mavros/state
这是用来订阅/mavros/state这一话题,可以实时查看当前无人机状态,如果connected显示的是True的话,则说明仿真运行正常,MAVROS通讯正常。显示的效果如下图所示:
如果安装了地面站的话执行下面指令打开地面站(到软件包对应目录)
./QGroundControl.AppImage
此时在地面站应该可以看到无人机相关状态信息,随后就进入到了最关键的一步,编写offboard控制节点,这个节点的功能包如果还没创建,可以参考下面这篇文章:
【ROS+Gazebo+px4】打开offboard模式,offboard_node文件内容-CSDN博客
而具体的源码分析,可以参考下面这篇文章:
mavros笔记(一):mavros概述与offboard例程解析_听风南巷的博客-CSDN博客
首先从最开始运行的 mavros_posix_sitl.launch 这一launch文件说起,下面是这个launch文件源码
<?xml version="1.0"?> <launch> <!-- MAVROS posix SITL environment launch script --> <!-- launches MAVROS, PX4 SITL, Gazebo environment, and spawns vehicle --> <!-- vehicle pose --> <arg name="x" default="0"/> <arg name="y" default="0"/> <arg name="z" default="0"/> <arg name="R" default="0"/> <arg name="P" default="0"/> <arg name="Y" default="0"/> <!-- vehicle model and world --> <arg name="est" default="ekf2"/> <arg name="vehicle" default="iris"/> <arg name="world" default="$(find mavlink_sitl_gazebo)/worlds/empty.world"/> <arg name="vehicle_sdf" default="iris"/> <arg name="sdf" default="$(find mavlink_sitl_gazebo)/models/$(arg vehicle_sdf)/$(arg vehicle_sdf).sdf"/> <!-- gazebo configs --> <arg name="gui" default="true"/> <arg name="debug" default="false"/> <arg name="verbose" default="true"/> <arg name="paused" default="false"/> <arg name="respawn_gazebo" default="false"/> <!-- MAVROS configs --> <arg name="fcu_url" default="udp://:24540@localhost:34580"/> <arg name="respawn_mavros" default="false"/> <!-- PX4 configs --> <arg name="interactive" default="true"/> <!-- PX4 SITL and Gazebo --> <include file="$(find px4)/launch/posix_sitl.launch"> <arg name="x" value="$(arg x)"/> <arg name="y" value="$(arg y)"/> <arg name="z" value="$(arg z)"/> <arg name="R" value="$(arg R)"/> <arg name="P" value="$(arg P)"/> <arg name="Y" value="$(arg Y)"/> <arg name="world" value="$(arg world)"/> <arg name="vehicle" value="$(arg vehicle)"/> <arg name="sdf" value="$(arg sdf)"/> <arg name="gui" value="$(arg gui)"/> <arg name="interactive" value="$(arg interactive)"/> <arg name="debug" value="$(arg debug)"/> <arg name="verbose" value="$(arg verbose)"/> <arg name="paused" value="$(arg paused)"/> <arg name="respawn_gazebo" value="$(arg respawn_gazebo)"/> </include> <!-- MAVROS --> <include file="$(find mavros)/launch/px4.launch"> <!-- GCS link is provided by SITL --> <arg name="gcs_url" value=""/> <arg name="fcu_url" value="$(arg fcu_url)"/> <arg name="respawn_mavros" value="$(arg respawn_mavros)"/> </include> </launch>
<arg>标签在6-11行最开始用于声明一些无人机初始位置和角度的变量,方便后续引入其他launch文件后调用,13-17用于定义世界模型和无人机模型的相关变量,后面根据官方注释的,是对Gazebo,MAVROS,PX4的初始化配置,这里要关注fcu_url这个变量,后续做集群的时候,可能会修改这个变量后面的UDP端口。到了31行,来到了第一个重头戏,这里包含了一个新的launch文件,这个文件的源码如下图所示:
<?xml version="1.0"?> <launch> <!-- Posix SITL environment launch script --> <!-- launches PX4 SITL, Gazebo environment, and spawns vehicle --> <!-- vehicle pose --> <arg name="x" default="0"/> <arg name="y" default="0"/> <arg name="z" default="0"/> <arg name="R" default="0"/> <arg name="P" default="0"/> <arg name="Y" default="0"/> <!-- vehicle model and world --> <arg name="est" default="ekf2"/> <arg name="vehicle" default="iris"/> <arg name="world" default="$(find mavlink_sitl_gazebo)/worlds/empty.world"/> <arg name="sdf" default="$(find mavlink_sitl_gazebo)/models/$(arg vehicle)/$(arg vehicle).sdf"/> <env name="PX4_SIM_MODEL" value="$(arg vehicle)" /> <env name="PX4_ESTIMATOR" value="$(arg est)" /> <!-- gazebo configs --> <arg name="gui" default="true"/> <arg name="debug" default="false"/> <arg name="verbose" default="false"/> <arg name="paused" default="false"/> <arg name="respawn_gazebo" default="false"/> <!-- PX4 configs --> <arg name="interactive" default="true"/> <!-- PX4 SITL --> <arg unless="$(arg interactive)" name="px4_command_arg1" value="-d"/> <arg if="$(arg interactive)" name="px4_command_arg1" value=""/> <node name="sitl" pkg="px4" type="px4" output="screen" args="$(find px4)/build/px4_sitl_default/etc -s etc/init.d-posix/rcS $(arg px4_command_arg1)" required="true"/> <!-- Gazebo sim --> <include file="$(find gazebo_ros)/launch/empty_world.launch"> <arg name="gui" value="$(arg gui)"/> <arg name="world_name" value="$(arg world)"/> <arg name="debug" value="$(arg debug)"/> <arg name="verbose" value="$(arg verbose)"/> <arg name="paused" value="$(arg paused)"/> <arg name="respawn_gazebo" value="$(arg respawn_gazebo)"/> </include> <!-- gazebo model --> <node name="$(anon vehicle_spawn)" pkg="gazebo_ros" type="spawn_model" output="screen" args="-sdf -file $(arg sdf) -model $(arg vehicle) -x $(arg x) -y $(arg y) -z $(arg z) -R $(arg R) -P $(arg P) -Y $(arg Y)"/> </launch>
对这个源码我们简要过一下,前面其实大差不差,在31行启动了px4这个节点,具体源码我没细看,大致应该是运行PX4固件,后面会加载一个空模型,随后又启动了一个gazebo的仿真节点,大致就是这样,我们书归正传,接着分析mavros_posix_sitl.launch这个文件,32-46行,就是把最开始前面定义的节点,统统都赋值到posix_sitl.launch这个launch文件里的变量中,做了一个嵌套替换,到了49行,又引入了一个新的launch文件,这里我依旧把源码附到下面:
<launch> <!-- vim: set ft=xml noet : --> <!-- example launch script for PX4 based FCU's --> <arg name="fcu_url" default="/dev/ttyACM0:57600" /> <arg name="gcs_url" default="" /> <arg name="tgt_system" default="1" /> <arg name="tgt_component" default="1" /> <arg name="log_output" default="screen" /> <arg name="fcu_protocol" default="v2.0" /> <arg name="respawn_mavros" default="false" /> <include file="$(find mavros)/launch/node.launch"> <arg name="pluginlists_yaml" value="$(find mavros)/launch/px4_pluginlists.yaml" /> <arg name="config_yaml" value="$(find mavros)/launch/px4_config.yaml" /> <arg name="fcu_url" value="$(arg fcu_url)" /> <arg name="gcs_url" value="$(arg gcs_url)" /> <arg name="tgt_system" value="$(arg tgt_system)" /> <arg name="tgt_component" value="$(arg tgt_component)" /> <arg name="log_output" value="$(arg log_output)" /> <arg name="fcu_protocol" value="$(arg fcu_protocol)" /> <arg name="respawn_mavros" default="$(arg respawn_mavros)" /> </include> </launch>
这部分是启动mavros的相关节点,在这里又引入了一个新的launch文件 node.launch,这里依旧把源码附到下面:
<launch> <!-- vim: set ft=xml noet : --> <!-- base node launch file--> <arg name="fcu_url" /> <arg name="gcs_url" /> <arg name="tgt_system" /> <arg name="tgt_component" /> <arg name="pluginlists_yaml" /> <arg name="config_yaml" /> <arg name="log_output" default="screen" /> <arg name="fcu_protocol" default="v2.0" /> <arg name="respawn_mavros" default="false" /> <node pkg="mavros" type="mavros_node" name="mavros" required="$(eval not respawn_mavros)" clear_params="true" output="$(arg log_output)" respawn="$(arg respawn_mavros)"> <param name="fcu_url" value="$(arg fcu_url)" /> <param name="gcs_url" value="$(arg gcs_url)" /> <param name="target_system_id" value="$(arg tgt_system)" /> <param name="target_component_id" value="$(arg tgt_component)" /> <param name="fcu_protocol" value="$(arg fcu_protocol)" /> <!-- load blacklist, config --> <rosparam command="load" file="$(arg pluginlists_yaml)" /> <rosparam command="load" file="$(arg config_yaml)" /> </node> </launch>
可以看到,最终最核心的,就是启动mavros这个节点,以及上传一些参数到参数服务器。至此对整个框架有了一个大体的认识。
在运行完launch文件后,此时启动了许多的话题和服务,通过订阅和发布的方式就可以通过话题去控制和监测无人机,常用的控制指令基本都是基于话题的形式,服务相关目前用到的就是模式切换和无人机上锁解锁这两项,对于仿真而言,由于运行时启动的飞机模式是auto模式,此时就需要对其切换成OFFBOARD模式,而切换OFFBOARD模式必须发送大于100条以上的数据才可,在实际飞行中,切记不要在程序中切换飞行模式,切记,后续的offboard控制节点就比较简单了,ROS八股文,订阅消息,发布消息,在上面的CSDN文章也有详细的介绍了。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。