Pixhawk原生固件PX4之offboard

本文详细介绍了PX4飞控系统中的Offboard控制功能,包括如何通过ROS和MAVROS实现外部控制,以及如何设置Pixhawk飞控板进行Offboard模式飞行。还提供了C++例程帮助理解整个流程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

offboard

PX4中的offboard(暂译作外部控制)是一个非常强大的功能。可以接受来自外部的控制指令,按照目前的了解来看,offboard搭配上MAVROS以及类似于TX1/NUC板载计算器,在PX4这个稳定的飞控平台上加上视觉处理或者人工智能,大有可为

配置说明

官网上有一个外部控制的例程,让飞机起飞到2米的高度(x = 0, y = 0, z =0),这里使用的是ROS里面的坐标系,并不是PX4固件中的NED,MAVROS中已经完成了坐标转换,这一点的话暂时不用深究。

本文主要讲一讲使用数传以及Pixhawk飞控板的外部控制方法:所需的只是一台Ubuntu系统的电脑以及一架带有数传的飞机。首先还是环境的配置,这一篇博文已经讲的非常清楚了,不知道为什么就是想装ROS indigo + Gazebo7。按教程offboard仿真通过以后就可以上真机测试了。

需要做的只有三个步骤

  1. 配置Pixhawk上的Telema 2 修改SYS_COMPANION参数改成Companion Link(57600)
    comp
  2. 将飞控连上MAVROS

    roslaunch mavros px4.launch fcu_url:=serial:///dev/ttyUSB0:57600
  3. 运行外部控制例程

    rosrun offb_ctrl offb_ctrl_node

    搞定 起飞了

    • 其中offboard的C++例程如下
/**
 * @file offb_node.cpp
 * @brief offboard example node, written with mavros version 0.14.2, px4 flight
 * stack and tested in Gazebo SITL
 */

#include <ros/ros.h>
#include <geometry_msgs/PoseStamped.h>
#include <mavros_msgs/CommandBool.h>
#include <mavros_msgs/SetMode.h>
#include <mavros_msgs/State.h>

mavros_msgs::State current_state;
void state_cb(const mavros_msgs::State::ConstPtr& msg){
    current_state = *msg;
}

int main(int argc, char **argv)
{
    ros::init(argc, argv, "offb_node"); //节点重命名为offb_node 供ROS调用
    ros::NodeHandle nh; // 打开roscpp节点

    ros::Subscriber state_sub = nh.subscribe<mavros_msgs::State>
            ("mavros/state", 10, state_cb);// 订阅函数的参数1表示主题  参数2表示缓存的消息队列长度  消息3表示消息更新时调用的回调函数
    ros::Publisher local_pos_pub = nh.advertise<geometry_msgs::PoseStamped> // 公告发布者的主题,参数2表示输出到订阅者的最大消息队列长度
            ("mavros/setpoint_position/local", 10);
    ros::ServiceClient arming_client = nh.serviceClient<mavros_msgs::CommandBool>
            ("mavros/cmd/arming"); // 创建一个客户端用来解锁
    ros::ServiceClient set_mode_client = nh.serviceClient<mavros_msgs::SetMode>
            ("mavros/set_mode"); // 创建一个客户端来设置模式

    //the setpoint publishing rate MUST be faster than 2Hz
    ros::Rate rate(20.0);

    // wait for FCU connection
    while(ros::ok() && current_state.connected){
        ros::spinOnce();
        rate.sleep();
    }

    geometry_msgs::PoseStamped pose;
    pose.pose.position.x = 2;
    pose.pose.position.y = 2;
    pose.pose.position.z = 2;

    //send a few setpoints before starting
    for(int i = 100; ros::ok() && i > 0; --i){
        local_pos_pub.publish(pose);
        ros::spinOnce();
        rate.sleep(); // 保证更新频率为20Hz,自动调整睡眠时间
    }

    mavros_msgs::SetMode offb_set_mode;
    offb_set_mode.request.custom_mode = "OFFBOARD"; // 调用者请求

    mavros_msgs::CommandBool arm_cmd;
    arm_cmd.request.value = true;

    ros::Time last_request = ros::Time::now();

    while(ros::ok()){
        if( current_state.mode != "OFFBOARD" &&
            (ros::Time::now() - last_request > ros::Duration(5.0))){
            if( set_mode_client.call(offb_set_mode) &&
                offb_set_mode.response.success){ // 被调用者响应
                ROS_INFO("Offboard enabled");
            }
            last_request = ros::Time::now();
        } else {
            if( !current_state.armed &&
                (ros::Time::now() - last_request > ros::Duration(5.0))){
                if( arming_client.call(arm_cmd) &&
                    arm_cmd.response.success){
                    ROS_INFO("Vehicle armed");
                }
                last_request = ros::Time::now();
            }
        }

        local_pos_pub.publish(pose);

        ros::spinOnce();
        rate.sleep();
    }

    return 0;
}
  • 关于ROS坐标系与PX4坐标系的转换

frame

如图所示:iris四旋翼蓝色桨对应的为机头方向。
ROS中的坐标是ENU(东北天)坐标系,而PX4中是NED(北东地)坐标系。MAVROS这个ROS包中已经进行了坐标转换。

通过ROS节点控制PX4飞机的位置时,坐标有如下的对应关系

ROSPX4
xy
yx
zalt(-z)

进行控制时要把ROS坐标系跟PX4的坐标系分离开来,摄像头坐标系Z轴沿光轴向下,X轴朝机头方向,根据右手法则确定Y轴指向飞机右侧。使用AprilTagArUco库可以直接通过相应编码的二维码得到飞机的位置姿态。对于位置误差

err_x = pose.x;
err_y = -pose.y;
err_z = -pose.z;

根据位置误差可以得到速度的设定值

ha

  • 目前存在的问题:

    1. 没有GPS或者辅助定位装置,这种直接设置位置的飞行是如何办到的?
    2. MAVROS运行时,offboard模式无法打断,遥控器都切不过去,危险
    3. ROS都不会,哪么搞?

    问题2的话直接采用手动设定模式的方法即可

奇技淫巧

Nomachine是一款高级的远程桌面访问工具。
怎么说呢,机载协同计算机(跑着Ubuntu系统)上装一个这个软件作为目的主机,然后本地计算机(Windows或者Ubuntu系统的电脑)上也装上这个软件,只要两台计算机在连在同一个局域网中,就能在本地操作飞机上的计算机了。
直接远程控制飞机上的电脑,QQ远程协助用过吧

haha

就像上面这样,在win7上可以操作另一台Ubuntu主机,这时你就可以进Ubuntu的Terminal跑你想运行的ROS节点了。

而且操作也是非常简单

  1. 打开软件

    open

    可以看到这里已经搜到一个网内的客户机了

  2. 点击连接(Connect)

    connect

    这里我是用Win7控制Ubuntu,因此在这里需要输入目标主机Ubuntu的账号密码,登陆后就可以看到上面图中显示的Ubuntu界面了。

  3. 操作说明

    close

    就但是远程协助那样去操作就行了。
    这里要介绍的是退出操作,从客户机退出需要将鼠标移动到画面的右上角,点下去你就知道了。

软件面向用户的体验做的不错,人人都能直接上手,赞一个!

TroubleShooting

  • GeographicLib报错

    [FATAL] [1506043767.570923014]: UAS: GeographicLib exception: File not readable /usr/share/GeographicLib/geoids/egm96-5.pgm | Run install_geographiclib_dataset.sh script in order to install Geoid Model dataset!
    [mavros-1] process has died [pid 14648, exit code -5, cmd /home/donghee/catkin_ws/devel/lib/mavros/mavros_node __name:=mavros __log:=/home/donghee/.ros/log/a61f72a6-9f34-11e7-80c3-7cb0c21790bc/mavros-1.log].
    log file: /home/donghee/.ros/log/a61f72a6-9f34-11e7-80c3-7cb0c21790bc/mavros-1*.log

    解决方案
    到catkin空间中下载mavros源码,并运行其中的脚本,应该是解决依赖性问题

    cd ~/catkin_ws/src/mavros/mavros/scripts
    sudo ./install_geographiclib_dataset.sh
### 设置和使用 PX4Offboard 模式 #### 一、准备工作 为了使车辆能够响应来自外部计算机的命令并进入离板模式,需确保 MAVLink 配置正确。这通常涉及配置串口或 UDP/TCP 连接参数以便于地面站软件(如 QGroundControl 或者 ROS 节点)与飞行控制器通信[^2]。 对于基于 ROS 和 MAVROS 功能包的应用场景来说,在启动 offboard 控制之前要先加载必要的 launch 文件来初始化节点间的交互环境,并确认话题和服务已经就绪可以被调用了[^3]。 ```bash roslaunch mavros px4.launch fcu_url:=<your_connection_string> ``` 其中 `<your_connection_string>` 应替换为实际连接字符串,例如 `tcp://192.168.1.10:5760` 表示通过 TCP 协议连接到 IP 地址为 192.168.1.10 的设备上的端口号 5760。 #### 二、编程接口介绍 当准备完毕之后就可以编写程序去改变飞机的状态至 ARMED 并切换成 OFFBOARD_MODE 。这里给出一段简单的 C++ 实现作为例子: ```cpp // 创建一个 Publisher 来发布位置设定点消息 geometry_msgs::PoseStamped pose; pose.pose.position.x = 0; // 设定目标坐标 (x, y, z) pose.pose.position.y = 0; pose.pose.position.z = ALTITUDE; pub_pose.publish(pose); // 发送初始设定点前等待 FCU 连接建立 while (!current_state.connected){ ros::spinOnce(); } // 请求切换到 OFFBOARD 模式 set_mode_client.call(offb_set_mode); if (offb_set_mode.response.mode_sent) { ROS_INFO("OFFBOARD enabled"); } else { ROS_ERROR("Failed to enable OFFBOARD mode."); } ``` 上述代码片段展示了如何利用 ROS 提供的服务客户端 API (`set_mode_client`) 向飞控发送请求以激活离板模式;同时也说明了怎样创建姿态设定点发布器(`pub_pose`)用于持续向系统输入期望的位置信息从而实现精确轨迹跟踪控制。 需要注意的是,在某些情况下可能会遇到 Failsafe 自动保护机制频繁触发的问题,这可能是由于信号丢失或者其他原因造成的。此时应该仔细检查硬件连线以及网络状况确保链路稳定可靠[^1]。 另外值得注意的一点就是,尽管进入了 OFFBOARD MODE ,但是仍然需要保持对安全性的关注——即在执行任何动作之前务必保证周围环境的安全性并且遵循当地法律法规的要求。
评论 13
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值