美文网首页
Topic in roscpp——Talker

Topic in roscpp——Talker

作者: 徐凯_xp | 来源:发表于2019-05-04 15:56 被阅读0次

    Topic是ROS里一种异步通信的模型,一般是节点间分工明确,有的只负责发送,有的只负责接收处理。对于绝大多数的机器人应用场景,比如传感器数据收发,速度控制指令的收发,Topic模型是最适合的通信方式。

    为了讲明白topic通信的编程思路,我们首先来看 topic_demo 中的代码,这个程序是一个消息收发的例子:自定义一个类型为gps的消息(包括位置x,y和工作状态state信息),一个node以一定频率发布模拟的gps消息,另一个node接收并处理,算出到原点的距离。 源代码见 ROS-Academy-for-Beginners/topic_demo

    步骤

    1. package
    2. msg
    3. talker.cpp
    4. listener.cpp
    5. CMakeList.txt &package.xml
    1. 创建package
    cd ~/catkin_ws/src
    catkin_create_pkg topic_demo roscpp rospy std_msgs
    
    2.创建GPS信息
    cd topic_demo/
    mkdir msg
    cd msg
    vi gps.msg
    

    在代码中,我们会用到自定义类型的gps消息,因此就需要来自定义gps消息,在msg路径下创建 gps.msg : 见 topic_demo/msg/gps.msg

    string state #工作状态
    float32 x #x坐标
    float32 y #y坐标
    

    以上就定义了一个gps类型的消息,你可以把它理解成一个C语言中的结构体,类似于

    struct gps
    {
    string state;
    float32 x;
    float32 y;
    }
    

    在程序中对一个gps消息进行创建修改的方法和对结构体的操作一样:
    当你创建完了msg文件,记得修改 CMakeLists.txt 和 package.xml ,从而让系统能够编译自定义消息。

    在 CMakeLists.txt 中需要改动
    find_package(catkin REQUIRED COMPONENTS
    roscpp
    std_msgs
    message_generation #需要添加的地方
    )
    add_message_files(FILES gps.msg)
    # catkin在cmake之上新增的命令,指定从哪个消息文件生成
    generate_messages(DEPENDENCIES std_msgs)
    # catkin新增的命令,用于生成消息
    # DEPENDENCIES后面指定生成msg需要依赖其他什么消息,由于gps.msg用到了flaot32这种ROS标准消息,因此需要再把std_msgs作为依赖
    
    package.xml 中需要的改动
    <build_depend>message_generation</build_depend>
    <run_depend>message_runtime</run_depend>
    

    完成了以上所有工作,就可以回到工作空间,然后编译了。编译完成之后会在 devel 路径下生成 gps.msg 对应的头文件,头文件按照C++的语法规则定义了 topic_demo::gps 类型的数据.
    要在代码中使用自定义消息类型,只要#include <topic_demo/gps.h> ,然后声明,按照对结构体操作的方式修改内容即可。

    topic_demo::gps mygpsmsg;
    mygpsmsg.x = 1.6;
    mygpsmsg.y = 5.5;
    mygpsmsg.state = "working";
    

    消息发布节点

    定义完了消息,就可以开始写ROS代码了。通常我们会把消息收发的两端分成两个节点来写,一个节点就是一个完整的C++程序。见 topic_demo/src/talker.cpp

    #include<ros/ros.h>
    #include<topic_demo/gps.h>//自定义msg产生的头文件
    int main(int argc, char **argv){
        ros::init(argc, argv, "talker" ); //用于解析ROS参数,第三个参数为本节点名
        ros::NodeHandle nh; //实例化句柄,初始化node
        topic_demo::gps msg; //自定义gps消息并初始化
        msg.x = 1.0;
        msg.y = 1.0;
        msg.state = "working";
        ros::Publisher pub = nh.advertise<topic_demo::gps>("gps_info",1);
    //创建Publisher,往"gps_info"话题上发布消息,<>内放入需要publish的类型
    //返回一个publisher的对象,称之为pub
        pub.publish(msg);
        ros::Rate loop_rate(1.0);//定义发布频率1hz
        while(ros::ok()){//循环发布msg
            ...//处理msg
            msg.x = 1.03 * msg.x;
            msg.y = 1.03* msg.y;  
            ROS_INFO("Talker: GPS: x = %f, y = %f,msg.x, msg.y")//输出当前msg
            pub.publish(msg);//以1HZ频率发布msg
            loop_rate.sleep(); 根据前面定义的loop_rate,设置1s的暂停
          }
        return 0;
    
    }
    

    机器人上几乎所有的传感器,几乎都是按照固定频率发布消息这种通信方式来传输数据,只是发布频率和数据类型的区别。

    相关文章

      网友评论

          本文标题:Topic in roscpp——Talker

          本文链接:https://www.haomeiwen.com/subject/wbixoqtx.html