当前位置:   article > 正文

ROS2机器人编程简述humble-第三章-BUMP AND GO IN C++ .3_ros2机器人编程实战 pdf

ros2机器人编程实战 pdf

简述本章项目,参考如下:

ROS2机器人编程简述humble-第三章-PERCEPTION AND ACTUATION MODELS .1

流程图绘制,参考如下:

ROS2机器人编程简述humble-第三章-COMPUTATION GRAPH .2

然后,在3.3和3.4分别用C++和Python编程实现

(br2_fsm_bumpgo_cpp/ + br2_fsm_bumpgo_py/)。

br2 fsm bumpgo cpp功能包组成如下:

  1. .
  2. ├── CMakeLists.txt
  3. ├── include
  4. │ └── br2_fsm_bumpgo_cpp
  5. │ └── BumpGoNode.hpp
  6. ├── launch
  7. │ └── bump_and_go.launch.py
  8. ├── package.xml
  9. └── src
  10. ├── br2_fsm_bumpgo_cpp
  11. │ └── BumpGoNode.cpp
  12. └── bumpgo_main.cpp
  13. 5 directories, 6 files

头文件:BumpGoNode.hpp
功能实现:BumpGoNode.cpp
主文件:bumpgo_main.cpp
启动文件:bump_and_go.launch.py

输入Subscription和输出Publisher:

  1. rclcpp::Subscription<sensor_msgs::msg::LaserScan>::SharedPtr scan_sub_;
  2. rclcpp::Publisher<geometry_msgs::msg::Twist>::SharedPtr vel_pub_;

回调支持:

  1. void scan_callback(const sensor_msgs::msg::LaserScan & msg);
  2. void scan_callback(sensor_msgs::msg::LaserScan::UniquePtr msg);
  3. void scan_callback(sensor_msgs::msg::LaserScan::SharedConstPtr msg);
  4. void scan_callback(const sensor_msgs::msg::LaserScan::SharedConstPtr & msg);
  5. void scan_callback(sensor_msgs::msg::LaserScan::SharedPtr msg);

依据需要选择,如:

  1. void scan_callback(sensor_msgs::msg::LaserScan::UniquePtr msg);
  2. void control_cycle();

更具体一些:

  1. void
  2. BumpGoNode::scan_callback(sensor_msgs::msg::LaserScan::UniquePtr msg)
  3. {
  4. last_scan_ = std::move(msg);
  5. }
  6. void
  7. BumpGoNode::control_cycle()
  8. {
  9. // Do nothing until the first sensor read
  10. if (last_scan_ == nullptr) {
  11. return;
  12. }
  13. geometry_msgs::msg::Twist out_vel;
  14. switch (state_) {
  15. case FORWARD:
  16. out_vel.linear.x = SPEED_LINEAR;
  17. if (check_forward_2_stop()) {
  18. go_state(STOP);
  19. }
  20. if (check_forward_2_back()) {
  21. go_state(BACK);
  22. }
  23. break;
  24. case BACK:
  25. out_vel.linear.x = -SPEED_LINEAR;
  26. if (check_back_2_turn()) {
  27. go_state(TURN);
  28. }
  29. break;
  30. case TURN:
  31. out_vel.angular.z = SPEED_ANGULAR;
  32. if (check_turn_2_forward()) {
  33. go_state(FORWARD);
  34. }
  35. break;
  36. case STOP:
  37. if (check_stop_2_forward()) {
  38. go_state(FORWARD);
  39. }
  40. break;
  41. }
  42. vel_pub_->publish(out_vel);
  43. }

里面可以看到四种状态切换:

  1. static const int FORWARD = 0;
  2. static const int BACK = 1;
  3. static const int TURN = 2;
  4. static const int STOP = 3;

状态对应和切换:

  1. void
  2. BumpGoNode::go_state(int new_state)
  3. {
  4. state_ = new_state;
  5. state_ts_ = now();
  6. }
  7. bool
  8. BumpGoNode::check_forward_2_back()
  9. {
  10. // going forward when deteting an obstacle
  11. // at 0.5 meters with the front laser read
  12. size_t pos = last_scan_->ranges.size() / 2;
  13. return last_scan_->ranges[pos] < OBSTACLE_DISTANCE;
  14. }
  15. bool
  16. BumpGoNode::check_forward_2_stop()
  17. {
  18. // Stop if no sensor readings for 1 second
  19. auto elapsed = now() - rclcpp::Time(last_scan_->header.stamp);
  20. return elapsed > SCAN_TIMEOUT;
  21. }
  22. bool
  23. BumpGoNode::check_stop_2_forward()
  24. {
  25. // Going forward if sensor readings are available
  26. // again
  27. auto elapsed = now() - rclcpp::Time(last_scan_->header.stamp);
  28. return elapsed < SCAN_TIMEOUT;
  29. }
  30. bool
  31. BumpGoNode::check_back_2_turn()
  32. {
  33. // Going back for 2 seconds
  34. return (now() - state_ts_) > BACKING_TIME;
  35. }
  36. bool
  37. BumpGoNode::check_turn_2_forward()
  38. {
  39. // Turning for 2 seconds
  40. return (now() - state_ts_) > TURNING_TIME;
  41. }

例如:

  1. bool
  2. BumpGoNode::check_forward_2_back()
  3. {
  4. // going forward when deteting an obstacle
  5. // at 0.5 meters with the front laser read
  6. size_t pos = last_scan_->ranges.size() / 2;
  7. return last_scan_->ranges[pos] < OBSTACLE_DISTANCE;
  8. }

检查机器人前方是否有障碍物。

主程序main:

  1. #include <memory>
  2. #include "br2_fsm_bumpgo_cpp/BumpGoNode.hpp"
  3. #include "rclcpp/rclcpp.hpp"
  4. int main(int argc, char * argv[])
  5. {
  6. rclcpp::init(argc, argv);
  7. auto bumpgo_node = std::make_shared<br2_fsm_bumpgo_cpp::BumpGoNode>();
  8. rclcpp::spin(bumpgo_node);
  9. rclcpp::shutdown();
  10. return 0;
  11. }

执行

启动仿真,参考:

ROS2机器人编程简述humble-第二章-SIMULATED ROBOT SETUP .4

ros2 launch br2_tiago sim.launch.py

加载避障程序:

ros2 run br2_fsm_bumpgo_cpp bumpgo --ros-args -r output_vel:=/nav_vel -r input_scan:=/scan_raw -p use_sim_time:=true

或者使用启动文件:

ros2 launch br2_fsm_bumpgo_cpp bump_and_go.launch.py

  1. from launch import LaunchDescription
  2. from launch_ros.actions import Node
  3. def generate_launch_description():
  4. bumpgo_cmd = Node(package='br2_fsm_bumpgo_cpp',
  5. executable='bumpgo',
  6. output='screen',
  7. parameters=[{
  8. 'use_sim_time': True
  9. }],
  10. remappings=[
  11. ('input_scan', '/scan_raw'),
  12. ('output_vel', '/nav_vel')
  13. ])
  14. ld = LaunchDescription()
  15. ld.add_action(bumpgo_cmd)
  16. return ld

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

闽ICP备14008679号