40template <
class ActionT>
41class ModeBase :
public px4_ros2::ModeBase
45 using Goal =
typename ActionContextType::Goal;
46 using Result =
typename ActionContextType::Result;
47 using Feedback =
typename ActionContextType::Feedback;
49 ModeBase(rclcpp::Node & node, Settings settings, std::shared_ptr<ActionContextType> action_context_ptr)
50 : px4_ros2::ModeBase{node, settings}, action_context_ptr_{action_context_ptr}
57 virtual void onActivateWithGoal(std::shared_ptr<const Goal> goal_ptr);
58 virtual void onDeactivateWithGoal(std::shared_ptr<const Goal> goal_ptr);
66 float dt_s, std::shared_ptr<const Goal> goal_ptr, std::shared_ptr<Feedback> feedback_ptr,
67 std::shared_ptr<Result> result_ptr) = 0;
68 virtual void updateSetpointOnCancel(
69 float dt_s, std::shared_ptr<const Goal> goal_ptr, std::shared_ptr<Feedback> feedback_ptr,
70 std::shared_ptr<Result> result_ptr);
74 void onDeactivate() override final;
75 void onActivate() override final;
76 void updateSetpoint(
float dt_s) override;
78 const std::shared_ptr<ActionContextType> action_context_ptr_;
81template <class ActionT>
82void ModeBase<ActionT>::onActivateWithGoal(std::shared_ptr<const Goal> )
86template <
class ActionT>
87void ModeBase<ActionT>::onDeactivateWithGoal(std::shared_ptr<const Goal> )
91template <
class ActionT>
92void ModeBase<ActionT>::updateSetpointOnCancel(
93 float , std::shared_ptr<const Goal> , std::shared_ptr<Feedback> ,
94 std::shared_ptr<Result> )
96 completed(px4_ros2::Result::Interrupted);
99template <
class ActionT>
100void ModeBase<ActionT>::onActivate()
102 onActivateWithGoal(action_context_ptr_->getGoalHandlePtr()->get_goal());
105template <
class ActionT>
106void ModeBase<ActionT>::onDeactivate()
108 const auto goal_handle_ptr = action_context_ptr_->getGoalHandlePtr();
109 onDeactivateWithGoal(goal_handle_ptr ? goal_handle_ptr->get_goal() :
nullptr);
112template <
class ActionT>
113void ModeBase<ActionT>::updateSetpoint(
float dt_s)
115 if (action_context_ptr_->isValid()) {
116 const auto goal_handle_ptr = action_context_ptr_->getGoalHandlePtr();
117 if (goal_handle_ptr->is_canceling()) {
118 updateSetpointOnCancel(
119 dt_s, goal_handle_ptr->get_goal(), action_context_ptr_->getFeedbackPtr(), action_context_ptr_->getResultPtr());
122 dt_s, goal_handle_ptr->get_goal(), action_context_ptr_->getFeedbackPtr(), action_context_ptr_->getResultPtr());
127template <
class ActionT>
128class PositionAwareMode :
public ModeBase<ActionT>
131 using typename ModeBase<ActionT>::ActionContextType;
134 rclcpp::Node & node, px4_ros2::ModeBase::Settings settings, std::shared_ptr<ActionContextType> action_context_ptr)
135 : ModeBase<ActionT>{node, settings, action_context_ptr}
137 vehicle_global_position_ptr_ = std::make_shared<px4_ros2::OdometryGlobalPosition>(*
this);
138 vehicle_local_position_ptr_ = std::make_shared<px4_ros2::OdometryLocalPosition>(*
this);
139 vehicle_attitude_ptr_ = std::make_shared<px4_ros2::OdometryAttitude>(*
this);
142 bool isGlobalPositionReached(
143 const Eigen::Vector3d & target_position_f_glob,
double reached_thresh_pos_m = 0.5,
144 double reached_thresh_vel_m_s = 0.3)
const;
146 bool isLocalPositionReached(
147 const Eigen::Vector3d & target_position_f_ned,
double reached_thresh_pos_m = 0.5,
148 double reached_thresh_vel_m_s = 0.3)
const;
150 bool isGlobalAltitudeReached(
151 float target_altitude_amsl_m,
double reached_thresh_pos_m = 0.5,
double reached_thresh_vel_m_s = 0.3)
const;
153 bool isLocalAltitudeReached(
154 float target_altitude_hagl_m,
double reached_thresh_pos_m = 0.5,
double reached_thresh_vel_m_s = 0.3)
const;
156 bool isHeadingReached(
float target_heading_rad,
double reached_thresh_heading_rad = 0.12)
const;
159 std::shared_ptr<px4_ros2::OdometryGlobalPosition> vehicle_global_position_ptr_;
160 std::shared_ptr<px4_ros2::OdometryLocalPosition> vehicle_local_position_ptr_;
161 std::shared_ptr<px4_ros2::OdometryAttitude> vehicle_attitude_ptr_;
164template <
class ActionT>
165bool PositionAwareMode<ActionT>::isGlobalPositionReached(
166 const Eigen::Vector3d & target_position_f_glob,
double reached_thresh_pos_m,
double reached_thresh_vel_m_s)
const
168 const float position_error_m =
169 px4_ros2::distanceToGlobalPosition(vehicle_global_position_ptr_->position(), target_position_f_glob);
170 return (position_error_m < reached_thresh_pos_m) &&
171 (vehicle_local_position_ptr_->velocityNed().norm() <= reached_thresh_vel_m_s);
174template <
class ActionT>
175bool PositionAwareMode<ActionT>::isLocalPositionReached(
176 const Eigen::Vector3d & target_position_f_ned,
double reached_thresh_pos_m,
double reached_thresh_vel_m_s)
const
178 const px4_msgs::msg::VehicleLocalPosition & pos = vehicle_local_position_ptr_->last();
179 const Eigen::Vector3d vec(pos.x, pos.y, pos.z);
180 const double position_error_m = (target_position_f_ned - vec).norm();
181 return (position_error_m < reached_thresh_pos_m) &&
182 (vehicle_local_position_ptr_->velocityNed().norm() <= reached_thresh_vel_m_s);
185template <
class ActionT>
186bool PositionAwareMode<ActionT>::isGlobalAltitudeReached(
187 float target_altitude_amsl_m,
double reached_thresh_pos_m,
double reached_thresh_vel_m_s)
const
189 Eigen::Vector3d target_position_f_glob = vehicle_global_position_ptr_->position();
190 target_position_f_glob.z() = target_altitude_amsl_m;
191 return isGlobalPositionReached(target_position_f_glob, reached_thresh_pos_m, reached_thresh_vel_m_s);
194template <
class ActionT>
195bool PositionAwareMode<ActionT>::isLocalAltitudeReached(
196 float target_altitude_hagl_m,
double reached_thresh_pos_m,
double reached_thresh_vel_m_s)
const
198 const px4_msgs::msg::VehicleLocalPosition & pos = vehicle_local_position_ptr_->last();
199 const Eigen::Vector3d target_position_f_ned(pos.x, pos.y, target_altitude_hagl_m);
200 return isLocalPositionReached(target_position_f_ned, reached_thresh_pos_m, reached_thresh_vel_m_s);
203template <
class ActionT>
204bool PositionAwareMode<ActionT>::isHeadingReached(
float target_heading_rad,
double reached_thresh_heading_rad)
const
206 const float heading_error_wrapped = px4_ros2::wrapPi(target_heading_rad - vehicle_attitude_ptr_->yaw());
207 return fabsf(heading_error_wrapped) <= fabsf(reached_thresh_heading_rad);
Helper class that stores contextual information related to a ROS 2 action.