当前位置:网站首页>[advanced ROS] lesson 5 TF coordinate transformation in ROS
[advanced ROS] lesson 5 TF coordinate transformation in ROS
2022-07-01 14:59:00 【Life is like Zhaoxu】
【ROS Advanced 】 The first five lectures ROS Medium TF Coordinate transformation

List of articles
Preface
In the introductory chapter ROS tutorial , We have simply studied about TF Content of coordinate transformation , The purpose of advanced chapter is to understand more deeply from the perspective of programming TF How to use coordinate transformation , And give static state 、 Dynamic and multi coordinate transformation And so on , Better grasp TF Function pack .
One 、TF Introduction to function package
1. Concept
- TF: namely TransForm Frame, Refers to coordinate transformation ;
- Coordinate system : That is, the position calibration system of the object , With Right hand coordinate system As the standard ;

- effect : Realize the transformation of points or vectors between different coordinate systems
2. TF2 And TF
- TF2: In the present ROS In the system ,TF2 The replacement has been 了 TF Use , It also includes the original functions ;
- difference :
- TF2 The function package corresponds to tf2、tf2_ros;TF The function package corresponds to tf package ,TF2 The feature pack of enhances cohesion , And internal differences API Completed subcontracting ;
- TF2 More efficient , Here is a demonstration of static coordinate transformation ;
- Static coordinate transformation demonstration : Because the information is fixed , so TF2 More efficient
- TF2:
Transform instruction :rosrun tf2_ros static_transform_publisher 0 0 0 0 0 0 /base_link /laser
Check the topic messages (rostopic):rostopic echo /tf( Cyclic output )- TF:
Transform instruction :rosrun tf static_transform_publisher 0 0 0 0 0 0 /base_link /laser 100
TF More startup parameters , There is a release frequency
Check the topic messages (rostopic):rostopic echo /tf_static( Single output )
- Common function packs :
- tf2_geometry_msgs: Can be ROS The message is converted to tf2 news .
- tf2: Encapsulates common messages of coordinate transformation .
- tf2_ros: by tf2 Provides roscpp and rospy binding , Encapsulates the commonly used coordinate transformation API.
- Refer to website address :ROS WIki TF2
3. Coordinate system viewing method
- Corresponding function package :tf2_tools, The installation instructions are as follows
sudo apt install ros-noetic-tf2-tools
- Tool use : Generate corresponding pdf file , Atlas presentation A tree structure
- Start the broadcast coordinate system program
- Run the toolkit instructions :
rosrun tf2_tools view_frames.py- The generated log is as follows :
[INFO] [1592920556.827549]: Listening to tf data during 5 seconds... [INFO] [1592920561.841536]: Generating graph in frames.pdf file...
- Open the pdf file :
evince frames.pdf
4. Coordinate information
- Commonly used msg Information :
- geometry_msgs/TransformStamped: It is used to transmit the position information related to the coordinate system
std_msgs/Header header # Header information uint32 seq #|-- Serial number time stamp #|-- Time stamp string frame_id #|-- coordinate ID string child_frame_id # Of the sub coordinate system id geometry_msgs/Transform transform # Coordinate information geometry_msgs/Vector3 translation # Offset float64 x #|-- X Offset of direction float64 y #|-- Y Offset of direction float64 z #|-- Z The offset in the direction geometry_msgs/Quaternion rotation # Four yuan number float64 x float64 y float64 z float64 w
- geometry_msgs/PointStamped: It is used to transmit the information of coordinate points in a coordinate system
std_msgs/Header header # head uint32 seq #|-- Serial number time stamp #|-- Time stamp string frame_id #|-- Of the coordinate system id geometry_msgs/Point point # Point coordinates float64 x #|-- x y z coordinate float64 y float64 z
- see msg Information command :
rosmsg info
Two 、 Static coordinate transformation
1. Scenario hypothesis
Question presentation : Suppose a robot model , The trunk body and the radar are respectively fixedly connected to two coordinate systems , The origin of the two coordinate system is located at the corresponding physical center , The displacement relationship between the radar origin and the torso origin is :x:0.2 y:0.0 z:0.5, In the radar coordinate system, the coordinate of an object is (2.0 3.0 5.0), Find the coordinates of this object in the torso coordinate system ?
3d Presentation under : The figure uses rviz Components , See the follow-up blog for specific usage

2. Programming to realize
- The basic idea :
- Create Feature Pack : Need to include tf2、tf2_ros、tf2_geometry_msgs、roscpp rospy std_msgs geometry_msgs etc.
- Create publisher : Release the relative relationship between torso coordinate system and radar coordinate
- Create subscribers : Subscribe to published information , According to the object information , With the help of TF The function package realizes coordinate transformation and output ;
notes :ROS The system also provides nodes for static coordinate conversion :
rosrun tf2_ros static_transform_publisher x Offset y Offset z Offset z angle of yaw y Pitch angle x Roll angle Parent coordinate system Sub coordinate system
- Publisher code :
/* Static coordinate transformation publisher : Release about laser Location information of coordinate system Implementation process : 1. Include header file 2. initialization ROS node 3. Create a static coordinate conversion broadcaster 4. Create coordinate system information 5. The broadcaster publishes coordinate system information 6.spin() */
// 1. Include header file
#include "ros/ros.h"
#include "tf2_ros/static_transform_broadcaster.h"
#include "geometry_msgs/TransformStamped.h"
#include "tf2/LinearMath/Quaternion.h"
int main(int argc, char *argv[])
{
setlocale(LC_ALL,"");
// 2. initialization ROS node
ros::init(argc,argv,"static_brocast");
// 3. Create a static coordinate conversion broadcaster
tf2_ros::StaticTransformBroadcaster broadcaster;
// 4. Create coordinate system information
geometry_msgs::TransformStamped ts;
//---- Set header information
ts.header.seq = 100;
ts.header.stamp = ros::Time::now();
ts.header.frame_id = "base_link";
//---- Set the child coordinate system
ts.child_frame_id = "laser";
//---- Set the offset of the child relative to the parent
ts.transform.translation.x = 0.2;
ts.transform.translation.y = 0.0;
ts.transform.translation.z = 0.5;
//---- Set quaternion : take Convert Euler angle data into quaternions
tf2::Quaternion qtn;
qtn.setRPY(0,0,0);
ts.transform.rotation.x = qtn.getX();
ts.transform.rotation.y = qtn.getY();
ts.transform.rotation.z = qtn.getZ();
ts.transform.rotation.w = qtn.getW();
// 5. The broadcaster publishes coordinate system information
broadcaster.sendTransform(ts);
ros::spin();
return 0;
}
- Subscriber code :
/* Subscribe to coordinate system information , Generate a relative to Coordinate point data of sub coordinate system , Convert to coordinate points in the parent coordinate system Implementation process : 1. Include header file 2. initialization ROS node 3. establish TF Subscription node 4. Generate a coordinate point ( Relative to the child coordinate system ) 5. Convert coordinate points ( Relative to the parent coordinate system ) 6.spin() */
//1. Include header file
#include "ros/ros.h"
#include "tf2_ros/transform_listener.h"
#include "tf2_ros/buffer.h"
#include "geometry_msgs/PointStamped.h"
#include "tf2_geometry_msgs/tf2_geometry_msgs.h" // Be careful : call transform Must contain the header file
int main(int argc, char *argv[])
{
setlocale(LC_ALL,"");
// 2. initialization ROS node
ros::init(argc,argv,"tf_sub");
ros::NodeHandle nh;
// 3. establish TF Subscription node
tf2_ros::Buffer buffer;
tf2_ros::TransformListener listener(buffer);
ros::Rate r(1);
while (ros::ok())
{
// 4. Generate a coordinate point ( Relative to the child coordinate system )
geometry_msgs::PointStamped point_laser;
point_laser.header.frame_id = "laser";
point_laser.header.stamp = ros::Time::now();
point_laser.point.x = 1;
point_laser.point.y = 2;
point_laser.point.z = 7.3;
// 5. Convert coordinate points ( Relative to the parent coordinate system )
// Create a new coordinate point , Used to receive conversion results
//-------------- Use try Statement or sleep , Otherwise, coordinate conversion may fail due to cache reception delay ------------------------
try
{
geometry_msgs::PointStamped point_base;
point_base = buffer.transform(point_laser,"base_link");
ROS_INFO(" Converted data :(%.2f,%.2f,%.2f), The reference coordinate system is :",point_base.point.x,point_base.point.y,point_base.point.z,point_base.header.frame_id.c_str());
}
catch(const std::exception& e)
{
// std::cerr << e.what() << '\n';
ROS_INFO(" Abnormal program .....");
}
r.sleep();
ros::spinOnce();
}
return 0;
}
3、 ... and 、 Dynamic coordinate transformation
1. Scenario hypothesis
Question presentation : Keyboard controls turtle movement , Dynamically release the relationship between the turtle coordinate system and the world coordinate system ;
3d demonstration (rviz):

2. Programming to realize
- The basic idea :
- Create Feature Pack : Dependencies contain tf2、tf2_ros、tf2_geometry_msgs、roscpp rospy std_msgs geometry_msgs、turtlesim;
- Create publisher : subscribe turtle1/pose, Get the tortoise in the world coordinate system x coordinate 、y coordinate 、 Offset, linear velocity and angular velocity , take pose Information is converted into relative information of coordinate system and released
- Create subscribers : Subscribe to relative information and output ;
- Publisher code :
/* Dynamic coordinate system relative attitude release ( The relative posture of one coordinate system relative to another coordinate system is constantly changing ) Implementation process : 1. Include header file 2. initialization ROS node 3. establish ROS Handle 4. Create subscription object 5. The callback function processes the subscribed data ( Realization TF radio broadcast ) 5-1. establish TF Broadcaster 5-2. establish Broadcast data ( adopt pose Set up ) 5-3. The broadcaster publishes data 6.spin */
// 1. Include header file
#include "ros/ros.h"
#include "turtlesim/Pose.h"
#include "tf2_ros/transform_broadcaster.h"
#include "geometry_msgs/TransformStamped.h"
#include "tf2/LinearMath/Quaternion.h"
void doPose(const turtlesim::Pose::ConstPtr& pose){
// 5-1. establish TF Broadcaster
static tf2_ros::TransformBroadcaster broadcaster;
// 5-2. establish Broadcast data ( adopt pose Set up )
geometry_msgs::TransformStamped tfs;
// |---- Head set
tfs.header.frame_id = "world";
tfs.header.stamp = ros::Time::now();
// |---- Coordinate system ID
tfs.child_frame_id = "turtle1";
// |---- Coordinate system relative information setting
tfs.transform.translation.x = pose->x;
tfs.transform.translation.y = pose->y;
tfs.transform.translation.z = 0.0; // Two dimensional implementation ,pose There is no z,z yes 0
// |--------- Quaternion settings
tf2::Quaternion qtn;
qtn.setRPY(0,0,pose->theta);
tfs.transform.rotation.x = qtn.getX();
tfs.transform.rotation.y = qtn.getY();
tfs.transform.rotation.z = qtn.getZ();
tfs.transform.rotation.w = qtn.getW();
// 5-3. The broadcaster publishes data
broadcaster.sendTransform(tfs);
}
int main(int argc, char *argv[])
{
setlocale(LC_ALL,"");
// 2. initialization ROS node
ros::init(argc,argv,"dynamic_tf_pub");
// 3. establish ROS Handle
ros::NodeHandle nh;
// 4. Create subscription object
ros::Subscriber sub = nh.subscribe<turtlesim::Pose>("/turtle1/pose",1000,doPose);
// 5. The callback function processes the subscribed data ( Realization TF radio broadcast )
//
// 6.spin
ros::spin();
return 0;
}
- Subscriber code :
//1. Include header file
#include "ros/ros.h"
#include "tf2_ros/transform_listener.h"
#include "tf2_ros/buffer.h"
#include "geometry_msgs/PointStamped.h"
#include "tf2_geometry_msgs/tf2_geometry_msgs.h" // Be careful : call transform Must contain the header file
int main(int argc, char *argv[])
{
setlocale(LC_ALL,"");
// 2. initialization ROS node
ros::init(argc,argv,"dynamic_tf_sub");
ros::NodeHandle nh;
// 3. establish TF Subscription node
tf2_ros::Buffer buffer;
tf2_ros::TransformListener listener(buffer);
ros::Rate r(1);
while (ros::ok())
{
// 4. Generate a coordinate point ( Relative to the child coordinate system )
geometry_msgs::PointStamped point_laser;
point_laser.header.frame_id = "turtle1";
point_laser.header.stamp = ros::Time();
point_laser.point.x = 1;
point_laser.point.y = 1;
point_laser.point.z = 0;
// 5. Convert coordinate points ( Relative to the parent coordinate system )
// Create a new coordinate point , Used to receive conversion results
//-------------- Use try Statement or sleep , Otherwise, coordinate conversion may fail due to cache reception delay ------------------------
try
{
geometry_msgs::PointStamped point_base;
point_base = buffer.transform(point_laser,"world");
ROS_INFO(" The coordinate point is relative to world The coordinates of the for :(%.2f,%.2f,%.2f)",point_base.point.x,point_base.point.y,point_base.point.z);
}
catch(const std::exception& e)
{
// std::cerr << e.what() << '\n';
ROS_INFO(" Abnormal program :%s",e.what());
}
r.sleep();
ros::spinOnce();
}
return 0;
}
notes : As for the advanced programming between dynamic coordinate transformations, in fact, the introduction of the introductory chapter shows the programming implementation of turtle tracking, that is, demonstration , Please read the introductory tutorial
Four 、 Multi coordinate transformation
1. Scenario hypothesis
- Question presentation : Suppose there are three coordinate systems , One of the coordinate systems is the parent coordinate system world, The other two are sub coordinate systems , The relative relationship between father and son is known , Find the relationship between two sub coordinate systems ;

2. Programming to realize
- The basic idea :
- Create Feature Pack : Dependencies contain tf2、tf2_ros、tf2_geometry_msgs、roscpp rospy std_msgs geometry_msgs、turtlesim
- Create publisher : Publish coordinate messages between parent and child coordinate systems
- Create subscribers : Subscription relativity , adopt TF Complete the conversion of two coordinate systems
- Publisher code : Use static coordinate transformation to publish
<launch>
<node pkg="tf2_ros" type="static_transform_publisher" name="son1" args="0.2 0.8 0.3 0 0 0 /world /son1" output="screen" />
<node pkg="tf2_ros" type="static_transform_publisher" name="son2" args="0.5 0 0 0 0 0 /world /son2" output="screen" />
</launch>
- Subscriber code :
/* Implementation process : 1. Include header file 2. initialization ros node 3. establish ros Handle 4. establish TF Subscription object 5. Parse the subscription information to get son1 The origin of the coordinate system is son2 The coordinates of analysis son1 The point in is relative to son2 Coordinates of 6.spin */
//1. Include header file
#include "ros/ros.h"
#include "tf2_ros/transform_listener.h"
#include "tf2/LinearMath/Quaternion.h"
#include "tf2_geometry_msgs/tf2_geometry_msgs.h"
#include "geometry_msgs/TransformStamped.h"
#include "geometry_msgs/PointStamped.h"
int main(int argc, char *argv[])
{
setlocale(LC_ALL,"");
// 2. initialization ros node
ros::init(argc,argv,"sub_frames");
// 3. establish ros Handle
ros::NodeHandle nh;
// 4. establish TF Subscription object
tf2_ros::Buffer buffer;
tf2_ros::TransformListener listener(buffer);
// 5. Parse the subscription information to get son1 The origin of the coordinate system is son2 The coordinates of
ros::Rate r(1);
while (ros::ok())
{
try
{
// analysis son1 The point in is relative to son2 Coordinates of
geometry_msgs::TransformStamped tfs = buffer.lookupTransform("son2","son1",ros::Time(0));
ROS_INFO("Son1 be relative to Son2 Coordinate relationship of : The parent coordinate system ID=%s",tfs.header.frame_id.c_str());
ROS_INFO("Son1 be relative to Son2 Coordinate relationship of : Sub coordinate system ID=%s",tfs.child_frame_id.c_str());
ROS_INFO("Son1 be relative to Son2 Coordinate relationship of :x=%.2f,y=%.2f,z=%.2f",
tfs.transform.translation.x,
tfs.transform.translation.y,
tfs.transform.translation.z
);
// Coordinate point analysis
geometry_msgs::PointStamped ps;
ps.header.frame_id = "son1";
ps.header.stamp = ros::Time::now();
ps.point.x = 1.0;
ps.point.y = 2.0;
ps.point.z = 3.0;
geometry_msgs::PointStamped psAtSon2;
psAtSon2 = buffer.transform(ps,"son2");
ROS_INFO(" stay Son2 The coordinates of :x=%.2f,y=%.2f,z=%.2f",
psAtSon2.point.x,
psAtSon2.point.y,
psAtSon2.point.z
);
}
catch(const std::exception& e)
{
// std::cerr << e.what() << '\n';
ROS_INFO(" Abnormal information :%s",e.what());
}
r.sleep();
// 6.spin
ros::spinOnce();
}
return 0;
}
summary
- Statement : The blog section of this section refers to CSDN User zhaoxuzuo ROS course , From the next blog ROS The advanced tutorial will step into ROSBAG On the basis of learning , Master this powerful ROS Record how the tool is used , Coming soon .

边栏推荐
- 【15. 区间合并】
- [Verilog quick start of Niuke question series] ~ use functions to realize data size conversion
- 22-06-26周总结
- 手把手带你入门 API 开发
- MongoDB第二话 -- MongoDB高可用集群实现
- Opencv Learning Notes 6 -- image feature [harris+sift]+ feature matching
- 【14. 区间和(离散化)】
- 【阶段人生总结】放弃考研,参与到工作中,已经顺利毕业了,昨天刚领毕业证
- Junda technology - wechat cloud monitoring scheme for multiple precision air conditioners
- TypeScript:const
猜你喜欢

Markdown编辑器使用基本语法

微信公众号订阅消息 wx-open-subscribe 的实现及闭坑指南
![[Verilog quick start of Niuke question series] ~ use functions to realize data size conversion](/img/e1/d35e1d382e0e945849010941b219d3.png)
[Verilog quick start of Niuke question series] ~ use functions to realize data size conversion

The State Administration of Chia Tai market supervision, the national development and Reform Commission and the China Securities Regulatory Commission jointly reminded and warned some iron ores

Blog recommendation | in depth study of message segmentation in pulsar

首届技术播客月开播在即

JVM第二话 -- JVM内存模型以及垃圾回收

对于编程思想和能力有重大提升的书有哪些?

Chapter 4 of getting started with MySQL: creation, modification and deletion of data tables

skywalking 6.4 分布式链路跟踪 使用笔记
随机推荐
skywalking 6.4 分布式链路跟踪 使用笔记
Opencv Learning Notes 6 -- image mosaic
保证生产安全!广州要求危化品企业“不安全不生产、不变通”
Reorganize the trivial knowledge points at the end of the term
TS报错 Don‘t use `object` as a type. The `object` type is currently hard to use
[15. Interval consolidation]
写在Doris毕业后的第一天
互联网医院系统源码 医院小程序源码 智慧医院源码 在线问诊系统源码
Flink 系例 之 TableAPI & SQL 与 MYSQL 分组统计
Word2vec yyds dry goods inventory
Use the npoi package of net core 6 C to read excel Pictures in xlsx cells and stored to the specified server
JVM第一话 -- JVM入门详解以及运行时数据区分析
Error-tf. function-decorated function tried to create variables on non-first call
[leetcode 324] swing sorting II thinking + sorting
Minimum spanning tree and bipartite graph in graph theory (acwing template)
Detailed explanation of ArrayList expansion, expansion principle [easy to understand]
Cannot link redis when redis is enabled
炎炎夏日,这份安全用气指南请街坊们收好!
tensorflow2-savedmodel convert to tflite
【天线】【3】CST一些快捷键
