35 #include <sensor_msgs/LaserScan.h> 36 #include <sensor_msgs/PointCloud.h> 37 #include <geometry_msgs/PoseStamped.h> 38 #include <geometry_msgs/Polygon.h> 39 #include <nav_msgs/Odometry.h> 42 #include <mrpt/version.h> 45 #include <mrpt/nav/reactive/CReactiveNavigationSystem.h> 46 #include <mrpt/maps/CSimplePointsMap.h> 48 using mrpt::maps::CSimplePointsMap;
50 #include <mrpt/version.h> 51 #if MRPT_VERSION >= 0x199 52 #include <mrpt/system/CTimeLogger.h> 53 #include <mrpt/config/CConfigFileMemory.h> 54 #include <mrpt/config/CConfigFile.h> 55 using namespace mrpt::system;
56 using namespace mrpt::config;
58 #include <mrpt/utils/CTimeLogger.h> 59 #include <mrpt/utils/CConfigFileMemory.h> 60 #include <mrpt/utils/CConfigFile.h> 64 #include <mrpt/system/filesystem.h> 66 #include <mrpt_bridge/pose.h> 67 #include <mrpt_bridge/point_cloud.h> 68 #include <mrpt_bridge/time.h> 70 #include <mrpt/kinematics/CVehicleVelCmd_DiffDriven.h> 82 ros::init(argc, argv,
"mrpt_reactivenav2d");
120 public mrpt::nav::CRobot2NavInterface
132 mrpt::math::TPose2D& curPose, mrpt::math::TTwist2D& curVel,
133 mrpt::system::TTimeStamp& timestamp,
134 mrpt::math::TPose2D& curOdometry, std::string& frame_id)
override 138 CTimeLoggerEntry tle(
139 m_parent.
m_profiler,
"getCurrentPoseAndSpeeds");
143 CTimeLoggerEntry tle2(
145 "getCurrentPoseAndSpeeds.lookupTransform_sensor");
156 mrpt::poses::CPose3D curRobotPose;
157 mrpt_bridge::convert(txRobotPose, curRobotPose);
159 mrpt_bridge::convert(txRobotPose.
stamp_, timestamp);
162 #if MRPT_VERSION >= 0x199 163 mrpt::poses::CPose2D(curRobotPose).asTPose();
165 mrpt::math::TPose2D(mrpt::poses::CPose2D(curRobotPose));
167 curOdometry = curPose;
170 MRPT_TODO(
"Retrieve current speeds from odometry");
172 "[getCurrentPoseAndSpeeds] Latest pose: %s",
173 curPose.asString().c_str());
175 curVel.vx = curV * cos(curPose.phi);
176 curVel.vy = curV * sin(curPose.phi);
188 const mrpt::kinematics::CVehicleVelCmd& vel_cmd)
override 190 using namespace mrpt::kinematics;
191 const CVehicleVelCmd_DiffDriven* vel_cmd_diff_driven =
192 dynamic_cast<const CVehicleVelCmd_DiffDriven*
>(&vel_cmd);
193 ASSERT_(vel_cmd_diff_driven);
195 const double v = vel_cmd_diff_driven->lin_vel;
196 const double w = vel_cmd_diff_driven->ang_vel;
198 "changeSpeeds: v=%7.4f m/s w=%8.3f deg/s", v,
200 geometry_msgs::Twist cmd;
207 bool stop(
bool isEmergency)
override 209 mrpt::kinematics::CVehicleVelCmd_DiffDriven vel_cmd;
212 return changeSpeeds(vel_cmd);
225 CSimplePointsMap& obstacles,
226 mrpt::system::TTimeStamp& timestamp)
override 228 timestamp = mrpt::system::now();
232 MRPT_TODO(
"TODO: Check age of obstacles!");
242 mrpt::kinematics::CVehicleVelCmd::Ptr ret =
243 mrpt::kinematics::CVehicleVelCmd::Ptr(
244 new mrpt::kinematics::CVehicleVelCmd_DiffDriven);
263 : m_auxinit(argc, argv),
266 m_1st_time_init(false),
267 m_target_allowed_distance(0.40
f),
269 m_pub_topic_reactive_nav_goal(
"reactive_nav_goal"),
270 m_sub_topic_local_obstacles(
"local_map_pointcloud"),
271 m_sub_topic_robot_shape(
""),
272 m_frameid_reference(
"/map"),
273 m_frameid_robot(
"base_link"),
274 m_save_nav_log(false),
275 m_reactive_if(*this),
276 m_reactive_nav_engine(m_reactive_if)
279 std::string cfg_file_reactive;
281 "cfg_file_reactive", cfg_file_reactive, cfg_file_reactive);
283 "target_allowed_distance", m_target_allowed_distance,
284 m_target_allowed_distance);
285 m_localn.
param(
"nav_period", m_nav_period, m_nav_period);
287 "frameid_reference", m_frameid_reference, m_frameid_reference);
288 m_localn.
param(
"frameid_robot", m_frameid_robot, m_frameid_robot);
290 "topic_robot_shape", m_sub_topic_robot_shape,
291 m_sub_topic_robot_shape);
292 m_localn.
param(
"save_nav_log", m_save_nav_log, m_save_nav_log);
296 !cfg_file_reactive.empty(),
297 "Mandatory param 'cfg_file_reactive' is missing!");
299 mrpt::system::fileExists(cfg_file_reactive),
300 "Config file not found: '%s'", cfg_file_reactive.c_str());
302 m_reactive_nav_engine.enableLogFile(m_save_nav_log);
308 CConfigFile cfgFil(cfg_file_reactive);
309 m_reactive_nav_engine.loadConfigFile(cfgFil);
311 catch (std::exception& e)
314 "Exception initializing reactive navigation engine:\n%s",
325 if (!m_sub_topic_robot_shape.empty())
327 m_sub_robot_shape = m_nh.
subscribe<geometry_msgs::Polygon>(
328 m_sub_topic_robot_shape, 1,
331 "Params say robot shape will arrive via topic '%s'... waiting " 333 m_sub_topic_robot_shape.c_str());
341 m_pub_cmd_vel = m_nh.
advertise<geometry_msgs::Twist>(
"cmd_vel", 1);
347 m_sub_nav_goal = m_nh.
subscribe<geometry_msgs::PoseStamped>(
348 m_pub_topic_reactive_nav_goal, 1,
350 m_sub_local_obs = m_nh.
subscribe<sensor_msgs::PointCloud>(
351 m_sub_topic_local_obstacles, 1,
369 "[navigateTo] Starting navigation to %s",
370 target.asString().c_str());
372 CAbstractPTGBasedReactive::TNavigationParamsPTG navParams;
373 CAbstractNavigator::TargetInfo target_info;
374 target_info.target_coords.x = target.x;
375 target_info.target_coords.y = target.y;
376 target_info.targetAllowedDistance = m_target_allowed_distance;
377 target_info.targetIsRelative =
false;
379 navParams.multiple_targets.push_back(target_info);
385 std::lock_guard<std::mutex> csl(m_reactive_nav_engine_cs);
386 m_reactive_nav_engine.navigate(&navParams);
395 if (!m_1st_time_init)
397 m_1st_time_init =
true;
399 "[ReactiveNav2DNode] Initializing reactive navigation " 402 std::lock_guard<std::mutex> csl(m_reactive_nav_engine_cs);
403 m_reactive_nav_engine.initialize();
406 "[ReactiveNav2DNode] Reactive navigation engine init done!");
409 CTimeLoggerEntry tle(m_profiler,
"onDoNavigation");
411 m_reactive_nav_engine.navigationStep();
416 geometry_msgs::PoseStamped trg = *trg_ptr;
418 "Nav target received via topic sub: (%.03f,%.03f, %.03fdeg) " 420 trg.pose.position.x, trg.pose.position.y,
421 trg.pose.orientation.z * 180.0 / M_PI, trg.header.frame_id.c_str());
424 if (trg.header.frame_id != m_frameid_reference)
428 geometry_msgs::PoseStamped trg2;
439 this->navigateTo(mrpt::math::TPose2D(
440 trg.pose.position.x, trg.pose.position.y, trg.pose.orientation.z));
445 std::lock_guard<std::mutex> csl(m_last_obstacles_cs);
446 mrpt_bridge::point_cloud::ros2mrpt(*obs, m_last_obstacles);
454 "[onRosSetRobotShape] Robot shape received via topic: " 457 mrpt::math::CPolygon poly;
458 poly.resize(newShape->points.size());
459 for (
size_t i = 0; i < newShape->points.size(); i++)
461 poly[i].x = newShape->points[i].x;
462 poly[i].y = newShape->points[i].y;
466 std::lock_guard<std::mutex> csl(m_reactive_nav_engine_cs);
467 m_reactive_nav_engine.changeRobotShape(poly);
473 int main(
int argc,
char** argv)
ros::NodeHandle m_localn
"~"
void onRosGoalReceived(const geometry_msgs::PoseStampedConstPtr &trg_ptr)
ReactiveNav2DNode(int argc, char **argv)
void publish(const boost::shared_ptr< M > &message) const
ros::Subscriber m_sub_robot_shape
Subscriber subscribe(const std::string &topic, uint32_t queue_size, void(T::*fp)(M), T *obj, const TransportHints &transport_hints=TransportHints())
virtual bool startWatchdog(float T_ms) override
MyReactiveInterface m_reactive_if
virtual void sendNavigationEndDueToErrorEvent()
ros::Subscriber m_sub_nav_goal
ROSCPP_DECL void init(int &argc, char **argv, const std::string &name, uint32_t options=0)
tf::TransformListener m_tf_listener
Use to retrieve TF data.
mrpt::kinematics::CVehicleVelCmd::Ptr getStopCmd() override
virtual void sendNavigationStartEvent()
void onRosLocalObstacles(const sensor_msgs::PointCloudConstPtr &obs)
void onRosSetRobotShape(const geometry_msgs::PolygonConstPtr &newShape)
std::string m_sub_topic_robot_shape
std::mutex m_last_obstacles_cs
std::string m_sub_topic_local_obstacles
ROSCPP_DECL void spin(Spinner &spinner)
ReactiveNav2DNode & m_parent
ros::Publisher m_pub_cmd_vel
std::string m_frameid_robot
virtual bool stopWatchdog() override
ros::Subscriber m_sub_local_obs
bool senseObstacles(CSimplePointsMap &obstacles, mrpt::system::TTimeStamp ×tamp) override
bool changeSpeeds(const mrpt::kinematics::CVehicleVelCmd &vel_cmd) override
bool param(const std::string ¶m_name, T ¶m_val, const T &default_val) const
#define ROS_ASSERT_MSG(cond,...)
TAuxInitializer m_auxinit
Just to make sure ROS is init first.
bool m_1st_time_init
Reactive initialization done?
std::mutex m_reactive_nav_engine_cs
Timer createTimer(Rate r, Handler h, Obj o, bool oneshot=false, bool autostart=true) const
std::string m_pub_topic_reactive_nav_goal
int main(int argc, char **argv)
ros::NodeHandle m_nh
The node handle.
Publisher advertise(const std::string &topic, uint32_t queue_size, bool latch=false)
MyReactiveInterface(ReactiveNav2DNode &parent)
virtual void sendNavigationEndEvent()
TFSIMD_FORCE_INLINE const tfScalar & w() const
mrpt::kinematics::CVehicleVelCmd::Ptr getEmergencyStopCmd() override
void onDoNavigation(const ros::TimerEvent &)
virtual void sendWaySeemsBlockedEvent()
#define ROS_INFO_STREAM(args)
double m_target_allowed_distance
bool getCurrentPoseAndSpeeds(mrpt::math::TPose2D &curPose, mrpt::math::TTwist2D &curVel, mrpt::system::TTimeStamp ×tamp, mrpt::math::TPose2D &curOdometry, std::string &frame_id) override
CSimplePointsMap m_last_obstacles
TAuxInitializer(int argc, char **argv)
CReactiveNavigationSystem m_reactive_nav_engine
ROSCPP_DECL void spinOnce()
ros::Timer m_timer_run_nav
bool stop(bool isEmergency) override
std::string m_frameid_reference
void navigateTo(const mrpt::math::TPose2D &target)
Issue a navigation command.