ROS与C++入门教程-初始化和关闭roscpp节点
ROS与C++入门教程-初始化和关闭roscpp节点
说明:
- 介绍roscpp节点的初始化和关闭
初始化
- 需要两步来初始化节点:
- 初始化节点:调用ros::init()函数来初始化节点,提供命令行参数给ROS,允许命名节点并提供不同的可选参数。
- 开始节点:调用ros::NodeHandle来启用节点
初始化节点
- 查阅 ros::init() API
- 在调用roscpp其他函数之前,必需先调用ros::init()。
- 两个常用的用法:
ros::init(argc, argv, "my_node_name");
- 或者
ros::init(argc, argv, "my_node_name", ros::init_options::AnonymousName);
- 一般情况下,符合如下形式:
void ros::init(<command line or remapping arguments>, std::string node_name, uint32_t options);
函数分析:
- argc 和 argv,参数列表,ROS使用这些来解析来自命令行的映射参数
- node_name,节点名,在ROS系统里必需是唯一的。如果有同名的节点启动,就会先自动关闭前面的,如果想启动多个相同节点,使用init_options::AnonymousName参数。
- options,这是一个可选的参数,可以指定某些选项,改变roscpp的行为。所以多个选项可以指定。选项在初始化选项部分中描述。
其他形式的 ros::init(),不使用argc/argv,而是使用复杂的映射参数,例如: std::map<std::string, std::string> 和std::vector<std::pair<std::string, std::string> >.
初始化节点简单的读取命令行参数和环境找出这样的节点名称、命名空间和重映射。
初始化没有连接到master主机,这需要在初始化后,再利用ros::master::check()或其他函数来检查主机状态。
初始化选项
- 查阅ros::init_options code API
- ros::init_options::NoSigintHandler
- 不要安装SIGINT处理器。在这种情况下,你应该安装自己SIGINT处理器,确保节点得到正确关闭时退出。
- 注意,SIGINT的默认动作是终止进程,所以如果你想做你自己的SIGTERM处理,你也要使用这个选项。
- ros::init_options::AnonymousName
- 匿名节点名称。将随机数添加到节点名称的结尾,使其成为唯一的。
- ros::init_options::NoRosout
- 不要广播rosconsole输出到/rosout话题。
访问命令行参数
- 正如上面提到的,调用ros::init()带有argc和argv参数,将从命令行清除ROS的参数。
- 如果你需要解析命令行之前调用ros::init(),你可以调用(新的ROS 0.10)ros::removeROSArgs()函数。
开始节点
- 最常用的方法开始节点:
ros::NodeHandle nh;
- 当第一个ros::NodeHandle创建时候,会调用ros::start()
- 最后一个ros::NodeHandle销毁时,会调用 ros::shutdown()
- 如果想自己管理节点的生命期,需要开始时调用ros::start(),在关闭程序前调用ros::shutdown()。
关闭节点
- 你可以在任何时间调用ros::shutdown()功能关闭节点。
- 这将关闭所有打开的订阅、发布、服务调用和服务服务器。
测试关闭
- 有两种方法检查关闭状态
- 最常用的方法是ros::ok(),如:
while (ros::ok())
{
...
}
- 一旦ros::ok() 返回false,节点就已经关闭。
- 另外一种方法: ros::isShuttingDown(),当ros::shutdown() 调用,就会返回true。
- 一般不鼓励使用,不过在一些高级用法中还是有用的。
- 例如在持续运行的服务节点的回调函数,当节点请求关闭的时候,回调函数应该立即关闭。这时候ros::isShuttingDown()就要用到,而 ros::ok() 就不能工作,因为主要回调函数在运行中,节点就不能关闭。
自定义信号处理器
- 你可以安装一个自定义的信号处理器,能跟ROS完美结合:
- 示例代码:
#include <ros/ros.h>
#include <signal.h>
void mySigintHandler(int sig)
{
// Do some custom action.
// For example, publish a stop message to some other nodes.
// All the default sigint handler does is call shutdown()
ros::shutdown();
}
int main(int argc, char** argv)
{
ros::init(argc, argv, "my_node_name", ros::init_options::NoSigintHandler);
ros::NodeHandle nh;
// Override the default ros sigint handler.
// This must be set after the first NodeHandle is created.
signal(SIGINT, mySigintHandler);
//...
ros::spin();
return 0;
}
获取最新文章: 扫一扫右上角的二维码加入“创客智造”公众号