ROS Exam Cheat Sheet

Important Stuff

Build:

catkin build

Source:

source ~/.bashrc

source ~/catkin_ws/devel/setup.bash

Create Package:

catkin_create_pkg <package name> <dependency 1> <dependency 2>

(From catkin_ws/src dir)

Go to where package is defined

roscd

Core:

Ros 1 is based on a single master node to control everything. Without this nothing will work. Normally auto started from a launch file. If its not started we can with

roscore

Launch:

roslaunch <package> <launch file>

A launch file is a xml file in the launch folder that defines a few things to launch

Example:

<launch>
  <node pkg="com2009_team17" type="avoidance_server.py" name="move_server" output="screen">
  </node>
  <node pkg="com2009_team17" type="exploration_client.py" name="exploration_client" output="screen">
  </node>
</launch>

(task2.launch)

Run:

rosrun <package> <exectuable file>

Launches a file marked as executable in the src folder of a package

Sub folder invariant (for some reason)

(chmod +x file.py)

Note: shebang is normally needed to tell os what to run this file with

#!/usr/bin/env python3

Nodes:

Overall explanation https://wiki.ros.org/ROS/Patterns/Communication#Communication_via_Topics_vs_Services_vs_X

rosnode list

List all available nodes

Nodes are things running that can pub and sub

Topics:

A message that is sent between nodes is put into a topic

For example the cmd_vel topic is for sending messages that control the robot’s speed

rostopic info /cmd_vel
rostopic list 
rostopic echo /chatter
rostopic pub /cmd_vel geometry_msgs/Twist[SPACE][TAB]

(to autofill)

Types:

Each message is formatted to a type Get information from rosmsg info

rosmsg info geometry_msgs/Twist

Custom types are .msg files in the msg folder

Services:

Request -> Response between specific nodes

One server, many clients

Synchronous: Has to wait for response from server before client can continue

To call (and autofill)

rosservice call /move_service[SPACE][TAB]

Info

rosservice info /move_service:

rosmsg but for service:

rossrv info tuos_msgs/SetBool

Request/response params seperated by a ---

Custom types are in srv folder (and, again, are .srv files)

Import into python:

from tuos_msgs.srv import Approach, ApproachResponse, ApproachRequest

# Service
self.service = rospy.Service(service_name, Approach, self.srv_callback)

def srv_callback(self, request_from_client):
	return ApproachResponse()

# Client
service = rospy.ServiceProxy(service_name, Approach)

request_to_server = ApproachRequest()

request_to_server.request_signal = True

response_from_server = service(request_to_server)

Actions:

Service but with feedback

Works using the standard pub sub commands with topics file

/camera_sweep_action_server/cancel
/camera_sweep_action_server/feedback
/camera_sweep_action_server/goal
/camera_sweep_action_server/result
/camera_sweep_action_server/status

Pub to goal to start

Sub to feedback to get the status

Define action file to set custom message types:

CameraSweep.action (in action folder, predictably)

#goal
float32 sweep_angle    # the angular sweep over which to capture images (degrees)
int32 image_count      # the number of images to capture during the sweep
---
#result
string image_path      # The filesystem location of the captured images
---
#feedback
int32 current_image    # the number of images taken
float32 current_angle  # the current angular position of the robot (degrees)

Status List

PENDING=0
ACTIVE=1
PREEMPTED=2
SUCCEEDED=3
ABORTED=4
REJECTED=5

Alt Text

Import custom actions (this is from file move.action)

from com2009_team17.msg import MoveAction, MoveGoal, MoveFeedback,MoveResult

# Server
self.actionserver = actionlib.SimpleActionServer(self.server_name,
MoveAction, self.action_server_launcher, auto_start=False)

# Client
self.client = actionlib.SimpleActionClient(action_server_name, MoveAction)
self.client.send_goal(self.goal, feedback_cb=self.feedback_callback, done_cb=self.done_callback)

Open CV:

Python image library

Need CvBridge to convert ros raw data to images

Crop image

cropped_img = cv_img[
    crop_z0:crop_z0+crop_height,
    crop_y0:crop_y0+crop_width
    ]

View hue/saturation graph

rosrun tuos_examples image_colours.py step2_cropping.jpg

We can create a mask to filter color values

We can find the centre of a detected area

https://theailearner.com/tag/image-moments-opencv-python/

  • M00: the sum of all non-zero pixels in the image mask (i.e. the size of the colour blob, in pixels)
  • M10: the sum of all the non-zero pixels in the horizontal (y) axis, weighted by row number
  • M01: the sum of all the non-zero pixels in the vertical (z) axis, weighted by column number
m = cv2.moments(img_mask)
cy = m['m10']/(m['m00']+1e-5)
cz = m['m01']/(m['m00']+1e-5) 

cv2 save image:

full_image_path = base_image_path.joinpath(f"lol.jpg")
cv2.imwrite(str(full_image_path), cropped_img)

cv2 display filtered image (with circle):

hsv_img = cv2.cvtColor(cropped_img, cv2.COLOR_BGR2HSV)

lower_threshold = (125, 100, 0)

upper_threshold = (200, 255, 255)

img_mask = cv2.inRange(hsv_img, lower_threshold, upper_threshold)

filtered_img = cv2.bitwise_and(cropped_img, cropped_img, mask = img_mask)
cv2.circle(
	filtered_img,
	(int(cy), int(cz)),
	10, (0, 0, 255), 2)
cv2.imshow("hehe", filtered_img)

PID Control:

Alt Text

\[u(t)=K_{P} e(t) + K_{I}\int e(t)dt + K_{D}\dfrac{d}{dt}e(t)\]

We can just use P or PI lol

Example for line following of filtered image:

kp = -0.03

reference_input = crop_width/2

feedback_signal = cy

error = feedback_signal - reference_input

ang_vel = kp * error

(then we can put ang_vel to robot)

Odometry

nav_msgs/Odometry contains 2 main elements

Pose is relative position/orientation from a set (usually starting) point. It is calculated from Inertial Measurement Board (on OpenCR board) as well as data from the wheel encoders

Twist is current linear/angular velocity (from just wheel encoders)

Orientation/Ang Vel is in quaternion form, convert to standard euler angles with:

from tf.transformations import euler_from_quaternion

(roll, pitch, yaw) = euler_from_quaternion([orientation.x, 
                     orientation.y, orientation.z, orientation.w], 
                     'sxyz')

Since this is a 2D wheeled robot we only care about X Y and yaw

Exact Examples of Commands

rosrun turtlebot3_teleop turtlebot3_teleop_key

Control robot with keys

rosrun rqt_graph rqt_graph

View node graph

roslaunch tuos_simulations rviz.launch

RViz

roslaunch turtlebot3_slam turtlebot3_slam.launch

RViz with SLAM stuff running

(rosrun map_server map_saver -f {map name})

Get map from running SLAM stuff

(eog {map name}.pgm)

Image viewer

catkin_create_pkg part1_pubsub rospy std_msgs

Create a basic package with ropy and standard messages

gzclient

Start gazebo if its been previously running headless

<command> | grep <something>

Filter the result of “command” to only lines that contain “something”

rosrun rqt_image_view rqt_image_view

RQT image view (live feed from cameras)

rostopic echo /chatter -nX

Echo the next X messages published to the ROS topic

rostopic echo /chatter -c

Clear the screen after a message is received (so it looks nicer)

cat ~/bash_alias

View the command aliases on a tuos ros system