Skip to content

Part 2 LaserScan Data

Tom Howard edited this page Jul 7, 2021 · 1 revision

Some suggestions for programming a /scan callback function

Configuring a subscriber within your code to subscribe to the /scan topic and obtain LaserScan data from the LiDAR sensor can be achieved as follows (assuming that you are using a Python Class structure):

self.subscriber = rospy.Subscriber('/scan', LaserScan, self.scan_callback)

You will also need to have imported the LaserScan message type correctly at the start of your code, like so:

from sensor_msgs.msg import LaserScan

The ranges part of the LaserScan message is what we are really interested in here and this is quite a large array of data (360 points: one distance measurement per degree around the robot). The numpy numeric library for Python can help with dealing with big data arrays such as this, and this module can be imported at the start of your code as shown below (assigning it to the name np for later use):

import numpy as np

With all this in place, a scan_callback could then be programmed to obtain a 40° arc of LaserScan data ahead of the robot:

def scan_callback(self, scan_data):
    # From the front of the robot, obtain a 20 degree 
    # arc of scan data either side of the x-axis 
    left_arc = scan_data.ranges[0:21]
    right_arc = scan_data.ranges[-20:]
    # combine the "left_arc" and "right_arc" data arrays, flip them so that 
    # the data is arranged from left (-20 degrees) to right (+20 degrees)
    # then convert to a numpy array
    front_arc = np.array(left_arc[::-1] + right_arc[::-1])

    # Create another numpy array which represents the angles 
    # (in degrees) associated with each of the data-points in 
    # the "front_arc" array above:
    arc_angles = np.arange(-20, 21)

    # Obtain the minimum distance measurement within the "front_arc" array,
    # determine the associated angle and broadcast this across the class 
    self.min_distance = front_arc.min()
    self.object_angle = arc_angles[np.argmin(front_arc)]

What's happening here is illustrated in the figure below, to hopefully make things clearer (if it isn't already):