ROS tf_tutorials整理

1. tutorial任务

坐标系描述

  • 如图所示,是一个tf_tree的坐标关系图,tutorial的任务是寻找turtle2和turtle1之间的位置关系,然后将turtle2移动到turtle1 的位置,对turtle1进行跟随。(先忽略/carrot1)

2. 流程

在这里插入图片描述

  • 首先创建/sim节点 rosrun turtlesim turtlesim_node,这里/sim节点名称由launch文件中定义<node pkg="turtlesim" type="turtlesim_node" name="sim"/>,也可以定义成其他名字;
  • /turtle1和/turtle2属于同一个节点/sim,/turtle1通过调用spawn服务生成了/turtle2 ,rosservice call /spawn <arg>...,实际是在listener节点创建的时候调用的(不太明白为什么没有加服务参数):
  ros::service::waitForService("spawn");
  //定义spawn服务客户端 add_turtle, 服务类型定义<turtlesim::Spawn>
  ros::ServiceClient add_turtle = node.serviceClient<turtlesim::Spawn>("spawn");
  turtlesim::Spawn srv;
  add_turtle.call(srv); //呼叫服务
  • /sim节点建立后,便会向/turtle1/pose和/turtle2/pose这两个主题上持续发送两个turtle的位置信息,该信息类型在/opt/ros/kinetic/share/turtlesim/msg/Pose.msg中定义:
float32 x
float32 y
float32 theta

float32 linear_velocity
float32 angular_velocity

编译的时候会将msg转换成对应的.h文件,供程序调用(具体细节不用知晓);

  • 但该信息不能直接用于强大的tf包来计算位置关系,必须转化成/tf内置的transform类型,这就是为什么我们需要/turtle1_tf_broadcaster和/turtle2_tf_broadcaster的原因,该两节点分别接受来自/turtle1/pose和/turtle2/pose的消息(订阅/turtle1/pose和/turtle2/pose两主题),然后使用sendTransform内置函数分别将/world到/turtle1的变换关系、/world到/turtle2的变换关系发送到/tf主题上,该消息类型定义在/opt/ros/kinetic/share/tf/msg/tfMessage.msg:
geometry_msgs/TransformStamped[] transforms

继续找/opt/ros/kinect/share/geometry_msgs/msg/TransformStamped.msg:

Header header
string child_frame_id # the frame id of the child frame
Transform transform

继续找/opt/ros/kinect/share/geometry_msgs/msg/Transform.msg

Vector3 translation
Quaternion rotation

破案了(可以继续往下找,但没必要了),该消息类型实际上就是一个 R 3 \mathcal{R}^3 R3的translation向量和一个 R 4 \mathcal{R}^4 R4的四元数向量,就可以表示一个三维空间中变换的所有信息。在tf中,你只需要把这些信息broadcast出来(例如坐标系a和坐标系b之间的变换关系,b和c之间的变换关系),tf就会自动生成一个tf_tree,记录所有坐标系的关系,而且,如果你需要知道a和c的关系,也可以直接读取,读取方式:

tf::StampedTransform transform;
tf::TransformListener listener;
listener.lookupTransform("/turtle2", "/turtle1", ros::Time(0), transform);

可以通过lookupTransform读取任意两个坐标系之间的位置关系,返回到transform中。(可以发现,无论是sendTransform还是lookupTransform,tf中用于数据传递使用的都是tf::StampedTransform数据类型,就像数据必须贴上邮票(stamp)才能发送一样,是不是很形象)

  • 建立listener节点。前面起始已经提到了,listener节点就是调用了lookupTransform,寻找了/turtle2和/turtle1之间的关系,并将该关系重新转换成可以控制turtle2节点运动的cmd_vel消息类型,发布在/turtle2/cmd_vel主题上,这样就实现了/turtle2对turtle1的跟随。
  • 详细代码参考TFtutorials
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值