Example programs for demonstrating data read from subscription of ROS 2.
These example programs consist of four pakages.
These are based on taker-listener in GitHub - ros2/demos at humble. If you know the talker-listener well, you can also understand these sample codes. Only intra_process_examples is based on demos/intra_process_demo/src/two_node_pipeline/two_node_pipeline.cpp at humble · ros2/demos exceptionally.
mkdir ros2_subscription_test
cd ros2_subscription_test
git clone [email protected]:takam5f2/ros2_subscription_examples.git
source /opt/ros/humble/setup.bash
colcon build --symlink-install --cmake-args -DCMAKE_BUILD_TYPE=Release
source install/setup.bashYou need two terminals one of which is for talker and another for listener.
Execute command below to run talker node on a terminal.
ros2 run simple_examples [talker node]The talker supports some additional options unlike the talker of GitHub - ros2/demos at humble. For example, you can change frequency of messages transmission by update_frequency option as below.
ros2 run simple_examples talker --ros-args -p update_frequency:=2.0If you want to use multiple options, you can add subsequent options as -p option_args:=<value>.
Below is the list of talker nodes included in simple_examples package.
talker- behavior
- it outputs a
/chattertopic message per specified frequency
- it outputs a
- option
update_frequency(float)- specify output frequency of messages
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Publisher
- default is false
- behavior
serialized_message_talker- behavior
- output
/chatterof SerializedMessage type per one second
- output
- no option
- behavior
Execute command below to run listener node on another terminal.
ros2 run simple_examples [listener node]The listener of ros2_subscription_examples/simple_examples at main · takam5f2/ros2_subscription_examples is driven by timer unlike the listener of GitHub - ros2/demos at humble which is driven by subscription of /chatter topic message.
Below is the list of listener nodes included in simple_examples package.
timer_listener- behavior
- It has a cyclic timer to execute a callback function in which a message is taken from a subscription
- It prints out string data, included in received
/chatter, to the terminal
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
printout_message_info(boolean)- enable to print MessageInfo
- default is false
- behavior
timer_batch_listener- behavior
- It has a cyclic timer to execute a callback function in which multiple messages are obtained from a subscription until the subscription queue becomes empty
- It prints out string data, included in received
/chatter, to the terminal
- option
update_frequency(float)- specify timer frequency
- default is 0.2
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
queue_size(integer)- specify Subscription Queue size which stores
/chattermessage
- specify Subscription Queue size which stores
- behavior
timer_listener_using_callback- behavior
- It has a cyclic timer to execute a callback function in which a message is taken from the subscription using
take_type_erased() handle_message()is called to execute a callback function which is registered to the subscription during execution of the timer-based callback function
- It has a cyclic timer to execute a callback function in which a message is taken from the subscription using
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_listener_using_normal_function- behavior
- It has a cyclic timer to execute a callback function in which a message is obtained from Subscription
- Another subroutine is called from the callback function to print out string data included in a received message
- this listener is similar to
timer_listener_using_callback, but it does not usehandle_message()
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_serialized_message_listener- behavior
- It has a cyclic timer to execute a callback function in which a message is obtained from Subscription
- the data type of the message is SerializedMessage
- this listener should run together with
serialized_message_talker
- option
update_frequency(float)- specify timer frequency
- default is 0.2
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
queue_size(integer)- specify Subscription Queue size which stores
/chattermessage
- specify Subscription Queue size which stores
- behavior
There are a few sample programs in intra_process_talker_listener in which a topic message is obtained by take_data() method and then processed by a callback function through execute() method. Intra-process communication requires a pair of publisher and subscription is located on a same Linux process. Then a pair of listener and talker must be launched as composable nodes. The package provides two sample launch files to start listener and talker on a composable nodes.
Execute command below to run talker_listener_intra_process.launch.py.
ros2 launch intra_process_talker_listener talker_listener_intra_process.launch.pyThe launch file supports some options. Below is an example to use use_intra_process_comms option.
ros2 launch intra_process_talker_listener talker_listener_intra_process.launch.py use_intra_process_comms:=falseIf use_intra_process_comms is set to false, communication between nodes is performed through DDS. If it is set to true, communication is performed through intra-process communication.
Below is the list of launch files included in intra_process_talker_listener package.
- talker_listener_intra_process.launch.py
- behavior
- It launches
talker_intra_processandtimer_listener_intra_process talker_intra_processtransmits/chattermessage andtimer_listener_intra_processreceives it- if
use_intra_process_commsis set totrue, intra-process communication is performed between the two nodes - if
use_intra_process_commsis set tofalse, a communication through DDS is performed between the two nodes
- It launches
- option
use_intra_process_comms(boolean)- enable intra-process communication
- default is true
talker_update_frequency(float)- specify frequency of publishing
/chattermessage bytalker_intra_process - default is 1.0
- specify frequency of publishing
listener_update_frequency(float)- specify timer frequency of
timer_listener_intra_process - default is 1.0
- specify timer frequency of
use_transient_local(boolean)- enable Transient Local of Publisher and Subscription
- default is false
- behavior
- talker_batch_listener_intra_process.launch.py
- behavior
- It launches
talker_intra_processandtimer_batch_listener_intra_process talker_intra_processtransmits/chattermessage andtimer_batch_listener_intra_processreceives ittimer_batch_listener_intra_processexecutes a callback function per five seconds in which topic messages are obtained from Subscription Queue until the queue becomes empty
- It launches
- option
use_intra_process_comms(boolean)- enable intra-process communication
- default is true
- behavior
As well as using composable nodes, intra-process communication also can be used between nodes on MultiThreadedExecutor to which they are registered, which you can see in intra_process_example.
/consumer and /producer nodes run in intra_process_example and /producer publishes a topic message and /consumer obtains it.
Execute two_node_pipeline_timer with the following command.
ros2 run intra_process_examples two_node_pipeline_timerIt has no particular option. A cyclic timer invokes the corresponding callback function. Another callback function, which is corresponding to the subscription, is called from the timer based callback function if a incoming message arrives. two_node_pipeline_timer shows two thread ID (TID); one is printed out from the timer based callback function and the other is from the subscription based one. They should be same number because their callback function should be executed on a same thread.
You need two terminals; one is for talker and the other for listener.
Launch a terminal and execute talker node with the following command.
ros2 run waitset_examples talker_tripleOnly talker_triple is provided as talker node in the waitset_examples package.
-
talker_triple-
behavior
- It transmits three kinds of topic messages;
/chatter,/slower_chatterand/slowest_chatter. They have different transmission frequency. /slower_chatterand/slowest_chatterare not transmitted if there is no corresponding subscription/chatteris transmitted at frequency defined byupdate_frequency/slower_chatteris transmitted at one half of frequency defined byupdate_frequency/slowest_chatteris transmitted at one third of frequency defined byupdate_frequency
- It transmits three kinds of topic messages;
-
option
update_frequency(float)- specify output frequency of messages
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Publisher
- default is false
-
Launch another terminal and execute a listener node with the following command.
ros2 run simple_examples [listener node]Below is the list of listener nodes included in the waitset_examples package.
timer_listener_single- behavior
- It has a cyclic timer to execute a callback function in which a
/chattermessage is obtained from Subscription Queue after arrival of a message is checked withrlcpp::WaitSet - It prints the obtained message by
RCLCPP_INFO
- It has a cyclic timer to execute a callback function in which a
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_listener_using_callback- behavior
- It has a cyclic timer to execute a callback function in which a
/chattermessage processed with the combination oftake_type_erased()andhandle_message()after arrival of a message is checked withrlcpp::WaitSet - It has the same behavior with
timer_listener_single
- It has a cyclic timer to execute a callback function in which a
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_listener_single_wait_some_period- behavior
- It has a cyclic timer to execute a callback function in which a
/chattermessage is obtained from Subscription Queue after arrival of a message is checked withrlcpp::WaitSet - Duration for timeout is given as the argument of
wait - It prints out string data in a incoming message if it receives the message by the duration
- Otherwise it prints out that timeout occurs during waiting a message
- It has a cyclic timer to execute a callback function in which a
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
waiting_time(float)- specify timeout value
- default is 4.0
- behavior
timer_batch_listener_single- behavior
- It has a cyclic timer to execute a callback function in which a
/chattermessage is obtained from Subscription Queue until the queue becomes empty after after arrival of a message is checked withrlcpp::WaitSet
- It has a cyclic timer to execute a callback function in which a
- option
update_frequency(float)- specify timer frequency
- default is 0.2
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
queue_size(integer)- specify Subscription Queue size
- default is 10
- behavior
timer_listener_triple_sync- behavior
- It has a cyclic timer to execute a callback function in which
/chatter,/slower_chatter, and/slowest_chattermessages are obtained from each Subscription Queue. If all of the three subscriptions have any message, they are taken at the same time - When all of the three subscriptions receive any message, they are taken from the subscriptions
rclcpp::WaitSettests whether or not all of the subscriptions receive any message
- It has a cyclic timer to execute a callback function in which
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_listener_triple_async- behavior
- It has a cyclic timer to execute a callback function in which
/chatter,/slower_chatter, and/slowest_chattermessages are obtained from each Subscription Queue. If one of the three subscriptions has any message, it is taken rclcpp::WaitSettests whether or not any of the subscriptions receives any message
- It has a cyclic timer to execute a callback function in which
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_listener_triple_separated_waitset- behavior
- Its behavior is same as that of
timer_listener_triple_async - It has three
rclcpp::WaitSetbased objects, each of which is provided per subscription while a singlerclcpp::WaitSetbased objects checks the three subscriptions intimer_listener_triple_async
- Its behavior is same as that of
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_listener_triple_sync_intra- behavior
- Its behavior is similar to that of
timer_listener_triple_sync - It supports intra-process communication unlike
timer_listener_triple_syncin which only inter-process communication can be used - To demonstrate intra-process communication with the node, executes the launch file with the following command.
ros2 launch waitset_examples talker_listener_triple_intra.launch.py use_intra_process_comms:=true- if
use_intra_process_commsis set to false, communication is performed through DDS
- Its behavior is similar to that of
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior
timer_listener_twin_static- behavior overview
- It has a cyclic timer to execute a callback function in which
/chatterand/slower_chattermessages are obtained from each Subscription Queue rclcpp::StaticWaitSetis used instead ofrclcpp::WaitSet- note that triggers can be registered to
rclcpp::StaticWaitSetonly at initialization unlikerclcpp::WaitSetto which triggers can be registered at any time - also refer to examples/rclcpp/wait_set/src/static_wait_set.cpp at rolling · ros2/examples
- It has a cyclic timer to execute a callback function in which
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior overview
timer_listener_twin_nested_waitset- behavior overview
- It has two cyclic timers; one of which is
timer_and another ismuch_slower_timer_ timer_is invoked at the given frequency to execute its callback functionmuch_slower_timer_is invoked per one tenth of frequency oftimer_much_slower_timer_has its callback function but it is not registered to Executor- the callback function of
timer_is executed periodically in which it is verified thatmuch_slower_timer_has been invoked or not by waitset - if yes, execute the callback function of
much_slower_timer_throughexecute_callback() - at that time it is verified that Subscription of
/slower_chatterhas been invoked or not by another waitset
- It has two cyclic timers; one of which is
- option
update_frequency(float)- specify timer frequency
- default is 1.0
use_transient_local(boolean)- enable Transient Local of Subscription
- default is false
- behavior overview