话题的发布与订阅

用RoboWare Studio创建好工作区和package后,在src下新建两个cpp文件,一个做话题的发布者,另一个做话题的订阅者,然后编译下就可以测试运行了,不过RoboWare只能调试运行一个节点,另一个可以用自带的集成终端(ctrl+`)或者新开一个终端运行,当然也可以写一个launch启动文件。

发布者:

//ros/ros.h是一个实用的头文件,它引用了ROS系统中大部分常用的头文件
#include "ros/ros.h"
//std_msgs/String存放在std_msgs package里,由String.msg文件自动生成的头文件
#include "std_msgs/String.h"
#include <sstream>


int main(int argc, char **argv)
{
    //初始化ROS,注意:名称必须唯一
    ros::init(argc,argv,"example1_a");

    //设置节点进程句柄
    ros::NodeHandle n;

    //告诉master我们将要在message topic上发布一个std_msgs/String的消息
    //参数一为发布的话题的名称;
    //参数二为缓冲区大小,如果我们发布的消息太快,缓冲区中的消息在大于1000个的时候就会开始丢弃先前发布的消息
    //NodeHandle::advertise() 返回一个 ros::Publisher对象,它有两个作用: 
    //1) 它有一个publish()成员函数可以让你在topic上发布消息; 2) 如果消息类型不对,它会拒绝发布
    ros::Publisher chatter_pub = n.advertise<std_msgs::String>("message",1000);

    //设置发送频率10Hz
    //ros::Rate对象可以允许你指定自循环的频率,自上一次调用Rate::sleep()后时间的流逝,并休眠直到一个频率周期的时间
    ros::Rate loop_rate(10);

    //ros::ok()返回false,如果下列条件之一发生:
    //1、SIGINT接收到(Ctrl-C)
    //2、被另一同名节点踢出ROS网络
    //3、ros::shutdown()被程序的另一部分调用
    //4、所有的ros::NodeHandles都已经被销毁 
    while(ros::ok())
    {
        //创建消息变量
        std_msgs::String msg;
        std::stringstream ss;
        ss << "Talker node sending message!";
        msg.data=ss.str();
        //ROS_INFO("%s",msg.data.c_str());  类似printf,输出检验

        //发布消息
        chatter_pub.publish(msg);

        //如果出现一个订阅者,ROS就会更新并读取所有主题
        //ROS消息回调处理函数ros::spin() 和 ros::spinOnce(),两者区别在于
        //前者调用后不会再返回,也就是你的主程序到这儿就不往下执行了,而后者在调用后还可以继续执行之后的程序
        ros::spinOnce();
        
        //休眠
        loop_rate.sleep();
    }
    return 0;
}

订阅者:

#include "ros/ros.h"
//ros/ros.h是一个实用的头文件,它引用了ROS系统中大部分常用的头文件
#include "std_msgs/String.h"
//std_msgs/String存放在std_msgs package里,由String.msg文件自动生成的头文件

//回调函数,当message topic消息到达后会调用此函数
void sub_callback(const std_msgs::String::ConstPtr& msg)
{
    ROS_INFO("I hear: [%s]",msg->data.c_str());
}


int main(int argc, char **argv)
{
    //初始化ROS,注意:名称必须唯一
    ros::init(argc, argv, "example1_b");

    //设置节点进程句柄
    ros::NodeHandle n;

    //参数一为订阅的话题名称(message);
    //参数二是消息缓存队列,这里设置为1000,即缓存了1000个消息后,如果由新的消息到达,则开始丢弃先前接收的消息;
    //参数三为当收到消息后调用的函数名称(sub_callback)
    ros::Subscriber sub = n.subscribe("message", 1000, sub_callback);
    
    //ros::spin()进入自循环,可以尽可能快的调用消息回调函数
    ros::spin();  
    return 0;
}

launch启动文件

<?xml version="1.0"?>
<launch>
 <node name = "example1_a" pkg = "chapter2_tutorials" type = "example1_a"/>
 <node name = "example1_b" pkg = "chapter2_tutorials" type = "example1_b"/>
</launch>
节点名、package包名字对应自己创建的进行更改,我的工作区东西比较多就不用tree列出来了。

将两个节点跑起来后,可以在终端输入rostopic echo /message 来查看话题发布的内容(message是我的话题名,可以根据自己的代码修改)。

图1、发布者

图2、订阅者

图3、工作区结构


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值