Nav2 Navigation Stack - lyrical  lyrical
ROS 2 Navigation Stack
input_at_waypoint.cpp
1 // Copyright (c) 2020 Samsung Research America
2 // Licensed under the Apache License, Version 2.0 (the "License");
3 // you may not use this file except in compliance with the License.
4 // You may obtain a copy of the License at
5 //
6 // http://www.apache.org/licenses/LICENSE-2.0
7 //
8 // Unless required by applicable law or agreed to in writing, software
9 // distributed under the License is distributed on an "AS IS" BASIS,
10 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 // See the License for the specific language governing permissions and
12 // limitations under the License.
13 
14 #include "nav2_waypoint_follower/plugins/input_at_waypoint.hpp"
15 
16 #include <string>
17 #include <exception>
18 
19 #include "pluginlib/class_list_macros.hpp"
20 
21 #include "nav2_ros_common/node_utils.hpp"
22 #include "nav2_ros_common/rate.hpp"
23 
24 namespace nav2_waypoint_follower
25 {
26 
27 using std::placeholders::_1;
28 
30 : input_received_(false),
31  is_enabled_(true),
32  timeout_(10.0, 0.0)
33 {
34 }
35 
37 {
38 }
39 
41  const nav2::LifecycleNode::WeakPtr & parent,
42  const std::string & plugin_name)
43 {
44  auto node = parent.lock();
45 
46  if (!node) {
47  throw std::runtime_error{"Failed to lock node in input at waypoint plugin!"};
48  }
49 
50  node_ = parent;
51  logger_ = node->get_logger();
52  clock_ = node->get_clock();
53 
54  double timeout;
55  std::string input_topic;
56  is_enabled_ = node->declare_or_get_parameter(
57  plugin_name + ".enabled", true);
58  input_topic = node->declare_or_get_parameter(
59  plugin_name + ".input_topic", std::string("input_at_waypoint/input"));
60  timeout = node->declare_or_get_parameter(
61  plugin_name + ".timeout", 10.0);
62  timeout_ = rclcpp::Duration(timeout, 0.0);
63 
64  RCLCPP_INFO(
65  logger_, "InputAtWaypoint: Subscribing to input topic %s.", input_topic.c_str());
66  subscription_ = node->create_subscription<std_msgs::msg::Empty>(
67  input_topic, std::bind(&InputAtWaypoint::Cb, this, _1));
68 }
69 
70 void InputAtWaypoint::Cb(const std_msgs::msg::Empty::ConstSharedPtr & /*msg*/)
71 {
72  std::lock_guard<std::mutex> lock(mutex_);
73  input_received_ = true;
74 }
75 
77  const geometry_msgs::msg::PoseStamped & /*curr_pose*/,
78  const int & curr_waypoint_index)
79 {
80  if (!is_enabled_) {
81  return true;
82  }
83 
84  input_received_ = false;
85 
86  auto node = node_.lock();
87  if (!node) {
88  RCLCPP_ERROR(logger_, "Failed to lock node in input at waypoint plugin.");
89  return false;
90  }
91 
92  rclcpp::Time start = clock_->now();
93  nav2::Rate r(node, 50);
94  bool input_received = false;
95  while (clock_->now() - start < timeout_) {
96  {
97  std::lock_guard<std::mutex> lock(mutex_);
98  input_received = input_received_;
99  }
100 
101  if (input_received) {
102  return true;
103  }
104 
105  r.sleep();
106  }
107 
108  RCLCPP_WARN(
109  logger_, "Unable to get external input at wp %i. Moving on.", curr_waypoint_index);
110  return false;
111 }
112 
113 } // namespace nav2_waypoint_follower
114 
115 PLUGINLIB_EXPORT_CLASS(
A sim-time-aware rate for Nav2 loops.
Definition: rate.hpp:61
Base class for creating a plugin in order to perform a specific task at waypoint arrivals.
Simple plugin based on WaypointTaskExecutor, let's robot to wait for a user input at waypoint arrival...
void initialize(const nav2::LifecycleNode::WeakPtr &parent, const std::string &plugin_name)
declares and loads parameters used
InputAtWaypoint()
Construct a new Input At Waypoint Arrival object.
void Cb(const std_msgs::msg::Empty::ConstSharedPtr &msg)
Processor callback.
~InputAtWaypoint()
Destroy the Input At Waypoint Arrival object.
bool processAtWaypoint(const geometry_msgs::msg::PoseStamped &curr_pose, const int &curr_waypoint_index)
Processor.