ROS message_filtersのお勉強
複数のトピックの時間の同期を取りたいときなどに使用する。
Time Synchronizer
- imageとcamera_infoの同期をとっている
The TimeSynchronizer filter synchronizes incoming channels by the timestamps contained in their headers, and outputs them in the form of a single callback that takes the same number of channels. The C++ implementation can synchronize up to 9 channels.
import message_filters from sensor_msgs.msg import Image, CameraInfo def callback(image, camera_info): # Solve all of perception here... image_sub = message_filters.Subscriber('image', Image) info_sub = message_filters.Subscriber('camera_info', CameraInfo) ts = message_filters.TimeSynchronizer([image_sub, info_sub], 10) ts.registerCallback(callback) rospy.spin()
#include <message_filters/subscriber.h> #include <message_filters/time_synchronizer.h> #include <sensor_msgs/Image.h> #include <sensor_msgs/CameraInfo.h> using namespace sensor_msgs; using namespace message_filters; void callback(const ImageConstPtr& image, const CameraInfoConstPtr& cam_info) { // Solve all of perception here... } int main(int argc, char** argv) { ros::init(argc, argv, "vision_node"); ros::NodeHandle nh; message_filters::Subscriber<Image> image_sub(nh, "image", 1); message_filters::Subscriber<CameraInfo> info_sub(nh, "camera_info", 1); TimeSynchronizer<Image, CameraInfo> sync(image_sub, info_sub, 10); sync.registerCallback(boost::bind(&callback, _1, _2)); ros::spin(); return 0; }
ApproximateTime Policy
The message_filters::sync_policies::ApproximateTime policy uses an adaptive algorithm to match messages based on their timestamp.
import message_filters from std_msgs.msg import Int32, Float32 def callback(mode, penalty): # The callback processing the pairs of numbers that arrived at approximately the same time mode_sub = message_filters.Subscriber('mode', Int32) penalty_sub = message_filters.Subscriber('penalty', Float32) ts = message_filters.ApproximateTimeSynchronizer([mode_sub, penalty_sub], 10, 0.1, allow_headerless=True) ts.registerCallback(callback) rospy.spin()
#include <message_filters/subscriber.h> #include <message_filters/synchronizer.h> #include <message_filters/sync_policies/approximate_time.h> #include <sensor_msgs/Image.h> using namespace sensor_msgs; using namespace message_filters; void callback(const ImageConstPtr& image1, const ImageConstPtr& image2) { // Solve all of perception here... } int main(int argc, char** argv) { ros::init(argc, argv, "vision_node"); ros::NodeHandle nh; message_filters::Subscriber<Image> image1_sub(nh, "image1", 1); message_filters::Subscriber<Image> image2_sub(nh, "image2", 1); typedef sync_policies::ApproximateTime<Image, Image> MySyncPolicy; // ApproximateTime takes a queue size as its constructor argument, hence MySyncPolicy(10) Synchronizer<MySyncPolicy> sync(MySyncPolicy(10), image1_sub, image2_sub); sync.registerCallback(boost::bind(&callback, _1, _2)); ros::spin(); return 0; }
参考:
http://wiki.ros.org/message_filters
message_filtersでタイムスタンプがおおよそ一致した際にコールバックさせる方法 - ゼロから始めるロボットプログラミング入門講座