Skip to content

A Simple Velocity Control Node (Move Circle)

The Initial Code

Start by returning to the publisher.py file from your part1_pubsub package (or return here), and copy the contents into your new move_circle.py file. Then, adapt the code as follows.

Creating the "Move Circle" Node

Imports

Once again, rclpy and the Node class from the rclpy.node library are vital for any node we create, so the first two imports will remain the same.

We need to import the message type used by the /cmd_vel topic here though, in order to be able to format velocity command messages appropriately. We can find all the necessary information about this message type by using the ros2 topic info command:

$ ros2 topic info /cmd_vel
Type: geometry_msgs/msg/Twist
...

And so our message import becomes:

from geometry_msgs.msg import Twist 

Change the Class Name

Previously our publisher class was called SimplePublisher(), change this to Circle:

class Circle(Node):

Initialising the Class

  1. Initialise the node with an appropriate name:

    super().__init__("move_circle")
    
  2. Change the create_publisher() parameters:

    self.my_publisher = self.create_publisher(
        msg_type=??, 
        topic=??, 
        qos_profile=10,
    )
    
  3. We'll need to publish velocity commands at a rate of at least 10 Hz, so set this here, and then set up a timer accordingly:

    publish_rate = 10 # Hz
    self.timer = self.create_timer(
        timer_period_sec=1/publish_rate, 
        callback=self.timer_callback
    )
    

Modifying the Timer Callback

Here, we'll publish our velocity commands:

def timer_callback(self):
    radius = 0.5 # meters
    linear_velocity = 0.1 # meters per second [m/s]
    angular_velocity = ?? 

    topic_msg = Twist() 
    topic_msg.linear.x = linear_velocity
    topic_msg.angular.z = angular_velocity
    self.my_publisher.publish(topic_msg) 

    self.get_logger().info( 
        f"Linear Velocity: {topic_msg.linear.x:.2f} [m/s], "
        f"Angular Velocity: {topic_msg.angular.z:.2f} [rad/s].",
        throttle_duration_sec=1, 
    )

Updating "Main"

Once again, don't forget to update any relevant parts of the main function to ensure that we're instantiating the Circle() class, spinning and shutting it down correctly.

← Back to Part 2