# Drive Kinematics: Skid Steer & Mecanum (ROS Twist included)

by David Kohanbash on June 22, 2016

Hi all

I am often in need of the basic kinematic motion equations for skid steer vehicles. I have also recently been working with mecanum wheeled vehicles. The skid steer equations are fairly simple and easy to find, however I will include it in different versions and include a ROS approach. The mecanum wheel equations are harder to find and there are different versions floating around. The first version I found had a lot of trig and mostly worked. The version I present here is easier to intuitively understand and seems to work better (I don’t need a random scale factor for this version), I also include a ROS approach for them.

## Skid Steer / Differential Drive

Here is some math for 2 and 4 wheel differential drive vehicles, 2 wheels and a castor, or skid steer tracked vehicles.

### Arc based commands

The basic skid steer equations are:

velocity_right =

w(RADIUS_OF_ARC_TO_DRIVE + WHEEL_BASE/2)

velocity_left =w(RADIUS_OF_ARC_TO_DRIVE – WHEEL_BASE/2)

In ROS if using the Twist message you will often set the linear.x, linear.y and angular.z fields.

Where *w* is the angular rotation, RADIUS_OF_ARC_TO_DRIVE is the arc radius that the robot should drive, and the WHEEL_BASE is the distance from the center of the left wheel to the center of the right wheel (See image above).

This can also be written as:

w= (velocity_right-velocity_left)/WHEEL_BASE

There are two special cases:

IF velocity_right == velocity_left :

THEN the radius of the arc is infinite so the robot will drive straight.IF velocity_right == -velocity_left :

THEN the radius of the arc is 0, and the robot rotates in place (ie. point turn)

### Linear & Angular Velocity Commands for ROS

In ROS if using the Twist topic (which is the default for drive messages) (message name is often cmd_vel) you will often set linear_velocity in the *linear.x* field and angular_velocity in the *angular.z* field.

velocity_left_cmd = (linear_velocity – angular_velocity * WHEEL_BASE / 2.0)/WHEEL_RADIUS;

velocity_right_cmd = (linear_velocity + angular_velocity * WHEEL_BASE / 2.0)/WHEEL_RADIUS;

## Mecanum Wheel Math

In ROS if using the Twist message you will often set the linear.x, linear.y and angular.z fields.

*One unrelated note is that if you are operating on uneven terrain then doing mecanum type motions will fail and have a lot of slip. Skid steer type motions will often work better (using the mecanum wheels).*WHEEL_SEPARATION_WIDTH = DISTANCE_LEFT_TO_RIGHT_WHEEL / 2

WHEEL_SEPARATION_LENGTH = DISTANCE_FRONT_TO_REAR_WHEEL / 2

### Forward kinematics

Wheel commands units are in rad/s

wheel_front_left = (1/WHEEL_RADIUS) * (linear.x – linear.y – (WHEEL_SEPARATION_WIDTH + WHEEL_SEPARATION_LENGTH)*angular.z);

wheel_front_right = (1/WHEEL_RADIUS) * (linear.x + linear.y + (WHEEL_SEPARATION_WIDTH + WHEEL_SEPARATION_LENGTH)*angular.z);

wheel_rear_left = (1/WHEEL_RADIUS) * (linear.x + linear.y – (WHEEL_SEPARATION_WIDTH + WHEEL_SEPARATION_LENGTH)*angular.z);

wheel_rear_right = (1/WHEEL_RADIUS) * (linear.x – linear.y + (WHEEL_SEPARATION_WIDTH + WHEEL_SEPARATION_LENGTH)*angular.z);

To drive a robot you will probably need to also invert one side since the motors are mounted opposite the other side. For example:

wheel_front_right = -1 * wheel_front_right

wheel_rear_right = -1 * wheel_rear_right

Also this gives an output in rad/s. If your motor controller is operating with encoder counts as the unit you will need to convert the units.

### Inverse Kinematics

linear.x = (wheel_front_left + wheel_front_right + wheel_rear_left + wheel_rear_right) * (WHEEL_RADIUS/4)

linear.y = ( -wheel_front_left + wheel_front_right + wheel_rear_left – wheel_rear_right) * (WHEEL_RADIUS/4)

angular.z = ( -wheel_front_left + wheel_front_right – wheel_rear_left + wheel_rear_right) * (WHEEL_RADIUS/(4 * (WHEEL_SEPARATION_WIDTH + WHEEL_SEPARATION_LENGTH)))

Source for mecanum wheel math: here. There are other versions of how to compute the wheel velocities but this is the one I like best.

I know this post was terser than most of my posts but I hope this math helps you.

## Comments

Please keep me informed.

Informed about what?

[…] the past we have looked at wheel design and the kinematics of skid steer and mecanum wheels. In this post we will take a quick look at different types of mobility types (ie. wheels, tracks, […]

Thank you very much for the kinematics code. I have one comment on the content, I’m fairly certain that the terms forward and inverse have been swapped around.

My understanding is that inverse kinematics is when you have a desired outcome in physical space and want to know what to set the motors to. While forward kinematics is when you know what the motors are doing and would like to calculate where the robot will go.

I forgot to enable notifications on my original comment.

How I phrased it above is how I (and others) talk about drive motions for wheels. It is not used the same as it is used with arms.

Technically you may be correct…