当前位置:   article > 正文

PX4中offboard模式_px4如何飞offboard模式

px4如何飞offboard模式
    1. /*
    2. 头文件,包括常见的geometry_msgs和mavros通信需要的mavros_msgs,添加上就行
    3. */
    4. #include <ros/ros.h>
    5. #include <geometry_msgs/PoseStamped.h>
    6. #include <mavros_msgs/CommandBool.h>
    7. #include <mavros_msgs/SetMode.h>
    8. #include <mavros_msgs/State.h>
    9. /*
    10. current_state表示的是无人机的状态,在主函数中订阅了对应的话题,这个状态就会不断更新,表示无人机当前的状态。state_cb就是对应的回调函数,会不断的执行,更新状态。现在先不用管为什么需要这个状态,后面的代码会解释。
    11. */
    12. mavros_msgs::State current_state;
    13. void state_cb(const mavros_msgs::State::ConstPtr& msg){
    14. current_state = *msg;
    15. }
    16. int main(int argc, char **argv)
    17. {
    18. ros::init(argc, argv, "offb_node");
    19. ros::NodeHandle nh;
    20. // 订阅无人机的状态
    21. ros::Subscriber state_sub = nh.subscribe<mavros_msgs::State>
    22. ("mavros/state", 10, state_cb);
    23. /*
    24. 发布一个geometry_msgs::PoseStamped的消息,需要知道的是,这个消息是控制无人机的一种方式,将指定坐标包裹进这个消息,然后发布出去,无人机就能自动飞行到指定的坐标地点
    25. */
    26. ros::Publisher local_pos_pub = nh.advertise<geometry_msgs::PoseStamped>
    27. ("mavros/setpoint_position/local", 10);
    28. /*
    29. 无人机有一个锁,如果不解锁,无人机虽然接受了命令但是不会动被锁住了,只有解锁了才能对无人机进行控制,下面这个服务调用就是用来请求解锁无人机。上面的current_state就包含了无人机是否解锁的信息,若没解锁就需要解锁,否则就不用,其用途在这就体现出来
    30. */
    31. ros::ServiceClient arming_client = nh.serviceClient<mavros_msgs::CommandBool>
    32. ("mavros/cmd/arming");
    33. /*
    34. 无人机飞行有很多种模式,如果需要用代码操控无人机,我们就需要切换到OFFBOARD模式。上面的current_state也包含了无人机当前的飞行模式,若不是OFFBOARD就需要切换到该模式。下面的这个服务调用就是用来请求切换无人机飞行模式。
    35. */
    36. ros::ServiceClient set_mode_client = nh.serviceClient<mavros_msgs::SetMode>
    37. ("mavros/set_mode");
    38. //the setpoint publishing rate MUST be faster than 2Hz
    39. /*
    40. 在OFFBOARD模式下,需要以>=2HZ的频率向无人机发送消息,否则无人机会回退到OFFBOARD模式之前所在的模式,因此这里的rate需要设置的比2大就行
    41. */
    42. ros::Rate rate(20.0);
    43. // wait for FCU connection
    44. /*
    45. 等待无人机与控制站连接(代码的方式就是代理),只有连接了才能发送消息
    46. */
    47. while(ros::ok() && !current_state.connected){
    48. ros::spinOnce();
    49. rate.sleep();
    50. }
    51. /*
    52. pose就是坐标,本实例是让无人机在2m处悬空,因此z设置为2,z表示的就是高度
    53. */
    54. geometry_msgs::PoseStamped pose;
    55. pose.pose.position.x = 0;
    56. pose.pose.position.y = 0;
    57. pose.pose.position.z = 1;
    58. // 下面这个感觉有没有都无所谓
    59. //send a few setpoints before starting
    60. for(int i = 100; ros::ok() && i > 0; --i){
    61. local_pos_pub.publish(pose);
    62. ros::spinOnce();
    63. rate.sleep();
    64. }
    65. // 请求的切换模式的消息,设置为OFFBOARD
    66. mavros_msgs::SetMode offb_set_mode;
    67. offb_set_mode.request.custom_mode = "OFFBOARD";
    68. // 请求解锁的消息,arm表示解锁,设置为true,disarm是上锁
    69. mavros_msgs::CommandBool arm_cmd;
    70. arm_cmd.request.value = true;
    71. // 记录上次请求的时间
    72. ros::Time last_request = ros::Time::now();
    73. while(ros::ok()){
    74. // 如果无人机模式不是OFFBOARD并且离上次操作时间大于5秒就发送请求切换,这里的5s是为了演示清楚设置的延时
    75. if( current_state.mode != "OFFBOARD" &&
    76. (ros::Time::now() - last_request > ros::Duration(5.0))){
    77. if( set_mode_client.call(offb_set_mode) &&
    78. offb_set_mode.response.mode_sent){
    79. ROS_INFO("Offboard enabled");
    80. }
    81. // 更新本次请求的时间
    82. last_request = ros::Time::now();
    83. } else {
    84. // 如果当前未解锁且与请求时间大于5s,就发送请求解锁
    85. if( !current_state.armed &&
    86. (ros::Time::now() - last_request > ros::Duration(5.0))){
    87. if( arming_client.call(arm_cmd) &&
    88. arm_cmd.response.success){
    89. ROS_INFO("Vehicle armed");
    90. }
    91. last_request = ros::Time::now();
    92. }
    93. }
    94. // 不断发送位置消息,但是只有解锁后才能真正开始运动,如果不发送就会退出OFFBOARD模式,因为请求发送速度要>=2HZ
    95. local_pos_pub.publish(pose);
    96. ros::spinOnce();
    97. rate.sleep();
    98. }
    99. return 0;
    100. }
  1. /**
  2. * @file offb_node.cpp
  3. * @brief Offboard control example node, written with MAVROS version 0.19.x, PX4 Pro Flight
  4. * Stack and tested in Gazebo SITL
  5. */
  6. #include <ros/ros.h>
  7. #include <geometry_msgs/PoseStamped.h>
  8. #include <mavros_msgs/CommandBool.h>
  9. #include <mavros_msgs/SetMode.h>
  10. #include <mavros_msgs/State.h>
  11. #include <nav_msgs/Odometry.h>//里程计信息格式
  12. int flag = 1;
  13. mavros_msgs::State current_state;
  14. nav_msgs::Odometry local_pos;
  15. void local_pos_cb(const nav_msgs::Odometry::ConstPtr& msg);
  16. void state_cb(const mavros_msgs::State::ConstPtr& msg);
  17. int main(int argc, char **argv)
  18. {
  19. ros::init(argc, argv, "offboard_multi_position");
  20. ros::NodeHandle nh;
  21. ros::Subscriber state_sub = nh.subscribe<mavros_msgs::State>("mavros/state", 10, state_cb);
  22. ros::Publisher local_pos_pub = nh.advertise<geometry_msgs::PoseStamped>("mavros/setpoint_position/local", 10);
  23. ros::Subscriber local_pos_sub = nh.subscribe<nav_msgs::Odometry>("/mavros/local_position/odom", 10, local_pos_cb);
  24. ros::ServiceClient arming_client = nh.serviceClient<mavros_msgs::CommandBool>("mavros/cmd/arming");
  25. ros::ServiceClient set_mode_client = nh.serviceClient<mavros_msgs::SetMode>("mavros/set_mode");
  26. //the setpoint publishing rate MUST be faster than 2Hz
  27. ros::Rate rate(20.0);
  28. // wait for FCU connection
  29. while(ros::ok() && !current_state.connected)
  30. {
  31. ros::spinOnce();
  32. rate.sleep();
  33. }
  34. geometry_msgs::PoseStamped pose;
  35. pose.pose.position.x = 0;
  36. pose.pose.position.y = 0;
  37. pose.pose.position.z = 0.3;
  38. //send a few setpoints before starting
  39. for(int i = 100; ros::ok() && i > 0; --i)
  40. {
  41. local_pos_pub.publish(pose);
  42. ros::spinOnce();
  43. rate.sleep();
  44. }
  45. mavros_msgs::SetMode offb_set_mode;
  46. offb_set_mode.request.custom_mode = "OFFBOARD";
  47. mavros_msgs::CommandBool arm_cmd;
  48. arm_cmd.request.value = true;
  49. ros::Time last_request = ros::Time::now();
  50. //此处满足一次请求进入offboard模式即可,官方例成循环切入offboard会导致无人机无法使用遥控器控制
  51. while(ros::ok())
  52. {
  53. //请求进入OFFBOARD模式
  54. if( current_state.mode != "OFFBOARD" && (ros::Time::now() - last_request > ros::Duration(5.0)))
  55. {
  56. if( set_mode_client.call(offb_set_mode) && offb_set_mode.response.mode_sent)
  57. {
  58. ROS_INFO("Offboard enabled");
  59. }
  60. last_request = ros::Time::now();
  61. }
  62. else
  63. {
  64. //请求解锁
  65. if( !current_state.armed && (ros::Time::now() - last_request > ros::Duration(5.0)))
  66. {
  67. if( arming_client.call(arm_cmd) && arm_cmd.response.success)
  68. {
  69. ROS_INFO("Vehicle armed");
  70. }
  71. last_request = ros::Time::now();
  72. }
  73. }
  74. if(ros::Time::now() - last_request > ros::Duration(5.0))
  75. {
  76. break;
  77. }
  78. local_pos_pub.publish(pose);
  79. ros::spinOnce();
  80. rate.sleep();
  81. }
  82. while(ros::ok())
  83. {
  84. if((flag == 1) && (ros::Time::now() - last_request > ros::Duration(5.0)))
  85. {
  86. ROS_INFO("Position_1");
  87. pose.pose.position.x = 0;
  88. pose.pose.position.y = 0;
  89. pose.pose.position.z = 0.3;
  90. last_request = ros::Time::now();
  91. flag=2;
  92. }
  93. if((flag ==2) && (ros::Time::now() - last_request > ros::Duration(8.0)))
  94. {
  95. ROS_INFO("Position_2 ");
  96. pose.pose.position.x = 0.5;
  97. pose.pose.position.y = 0;
  98. pose.pose.position.z = 0.3;
  99. last_request = ros::Time::now();
  100. flag=3;
  101. }
  102. if((flag ==3) && (ros::Time::now() - last_request > ros::Duration(8.0)))
  103. {
  104. ROS_INFO("Position_3 ");
  105. pose.pose.position.x = 0.5;
  106. pose.pose.position.y = 0.5;
  107. pose.pose.position.z = 0.3;
  108. last_request = ros::Time::now();
  109. flag=4;
  110. }
  111. if((flag ==4) && (ros::Time::now() - last_request > ros::Duration(8.0)))
  112. {
  113. ROS_INFO("Position_4 ");
  114. pose.pose.position.x = 0;
  115. pose.pose.position.y = 0.5;
  116. pose.pose.position.z = 0.3;
  117. last_request = ros::Time::now();
  118. flag=5;
  119. }
  120. if((flag ==5) && (ros::Time::now() - last_request > ros::Duration(8.0)))
  121. {
  122. ROS_INFO("Position_1 ");
  123. pose.pose.position.x = 0;
  124. pose.pose.position.y = 0;
  125. pose.pose.position.z = 0.3;
  126. last_request = ros::Time::now();
  127. flag=6;
  128. }
  129. if((flag ==6) && (ros::Time::now() - last_request > ros::Duration(8.0)))
  130. {
  131. break;
  132. }
  133. local_pos_pub.publish(pose);
  134. ros::spinOnce();
  135. rate.sleep();
  136. }
  137. ROS_INFO("AUTO.LAND");
  138. offb_set_mode.request.custom_mode = "AUTO.LAND";
  139. set_mode_client.call(offb_set_mode);
  140. return 0;
  141. }
  142. void state_cb(const mavros_msgs::State::ConstPtr& msg)
  143. {
  144. current_state = *msg;
  145. }
  146. void local_pos_cb(const nav_msgs::Odometry::ConstPtr& msg)
  147. {
  148. local_pos = *msg;
  149. }

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/羊村懒王/article/detail/688607
推荐阅读
相关标签
  

闽ICP备14008679号