Skip to main content
Version: 2023

Control Theory

Introduction

Control theory is a branch of mathematics that deals with the control of continuously operating dynamical systems in engineered processes and machines. The objective is to develop a control model for controlling such systems using a control action in an optimum manner without delay or overshoot and ensuring control stability.

To do this, a controller with the requisite corrective behavior is required.

In robotics, control theory is used to design controllers that can make robots perform desired tasks. Using the robot's sensors, the controller can determine the robot's current state and send commands to the robot's actuators to make it perform a desired task.

"Sense, plan, act." - Rodney Brooks

Open-loop vs. Closed-loop Control

There are two main types of control systems: open-loop and closed-loop.

Open-loop Control

In an open-loop control system, the control action from the controller is independent of the process variable. The process variable is the variable that is being controlled. The control action is the output of the controller that is sent to the system.

An example of an open-loop control system is an electric toaster. The toaster is turned on and operates for a predetermined time. The input is the button that is pressed to turn the toaster on, and the output is the amount of time the toaster stays on. There is no sensing of the toast temperature. As a result, the toaster provides the same output for any given input (i.e. the toaster provides the same amount of toasting for each button selection).

When you programmed your robot choreography, you used open-loop control. You programmed the robot to move for a certain amount of time, but the robot did not sense its environment and adjust its motion accordingly.

Closed-loop Control

In a closed-loop control system, the control action from the controller is dependent on feedback from the process in the form of the value of the process variable.

A closed-loop control system is also called a feedback control system.

feedback control system

An example of a closed-loop control system is the cruise control system in an automobile. The cruise control system monitors the car's speed and maintains the set speed without the driver's input. The controller continuously calculates an error signal as the difference between the desired speed (set point) and the actual speed, and applies a control action to reduce the error signal.

When you programmed your robot to follow a line, you used closed-loop control.

PID Control

PID control is a control loop feedback mechanism widely used in industrial control systems and a variety of other applications requiring continuously modulated control. It is one of the most commonly used control strategies in the industry.

A PID controller continuously calculates an error value as the difference between a desired setpoint and a measured process variable and applies a correction based on proportional, integral, and derivative terms (sometimes denoted P, I, and D respectively) which give their name to the controller type.

PID controller

Fun Fact

The first theoretical analysis and practical application was in the field of automatic steering systems for ships.

Mathematically, the PID controller is expressed as:

u(t)=Kpe(t)+Ki0te(τ)dτ+Kdde(t)dtu(t) = K_p e(t) + K_i \int_0^t e(\tau) d\tau + K_d \frac{de(t)}{dt}

where:

  • u(t)u(t) is the control signal (output of the controller)
  • e(t)=r(t)y(t)e(t) = r(t) - y(t) is the error signal (difference between the desired setpoint and the measured process variable).
  • KpK_p is the proportional gain
  • KiK_i is the integral gain
  • KdK_d is the derivative gain
  • 0te(τ)dτ\int_0^t e(\tau) d\tau is the integral term (sum of the error over time)
  • de(t)dt\frac{de(t)}{dt} is the derivative term (rate of change of the error)

Proportional Control

The proportional term (Kpe(t)K_p e(t)) makes a change to the output that is proportional to the current error value. The proportional response can be adjusted by multiplying the error by a constant KpK_p called the proportional gain.

In the case of the line-following robot, the error is the difference between the desired position (the center of the line) and the measured position (the position of the robot relative to the line). The proportional term makes the robot turn proportional to the error. The larger the error, the larger the turn.

In python, the proportional term is implemented as:

Kp = 1.0
error = desired_position - measured_position
proportional = Kp * error

Integral Control

The integral term (Ki0te(τ)dτK_i \int_0^t e(\tau) d\tau) makes a change to the output that is proportional to both the magnitude of the error and the duration of the error. The integral response can be adjusted by multiplying the error by a constant KiK_i called the integral gain.

In the case of the line-following robot, the integral term makes the robot turn proportional to the error and the duration of the error. The larger the error and the longer the error, the larger the turn.

In python, the integral term is implemented as:

Ki = 1.0
error = desired_position - measured_position
error_accumulator += error * dt # dt is the time since the last update
integral = Ki * error_accumulator

Integral Windup

The integral term accumulates the error over time. If the error is large and lasts for a long time, the integral term can become very large. This is called integral windup.

To prevent integral windup, the integral term is often limited to a maximum value.

In the above python code, the integral term is limited to a maximum value of 1.0:

integral = min(Ki * error_accumulator, 1.0)

Derivative Control

The derivative term (Kdde(t)dtK_d \frac{de(t)}{dt}) makes a change to the output that is proportional to the rate of change of the error. The derivative response can be adjusted by multiplying the error by a constant KdK_d called the derivative gain.

In the case of the line-following robot, the derivative term makes the robot turn proportional to the rate of change of the error. The larger the rate of change of the error, the larger the turn.

In python, the derivative term is implemented as:

Kd = 1.0
error = desired_position - measured_position
derivative = Kd * (error - previous_error) / dt # dt is the time since the last update
previous_error = error

Problem Set

For this problem set, you will fork and work on your own copy of the control-intro repository.

We will be using the SITL to simulate the underwater vehicle.

In a terminal on the backseat RPi, run the following command to start the SITL:

cd ~/ardupilot/ArduSub
../Tools/autotest/sim_vehicle.py --vehicle=ArduSub --aircraft="bwsibot" -L RATBeach --out=udp:YOUR_COMPUTER_IP:14550

Replace YOUR_COMPUTER_IP with the IP address of your computer.

You should now see a robot in QGroundControl.

Problem 1: Depth Control

In this problem, you will implement a PID controller to control the depth of a simulated underwater vehicle.

control-intro contains a python script called depth_control.py that runs a PID controller to control the depth of the vehicle.

pid.py contains a PID controller class that you can use to implement the PID controller.

  1. Fix the TODOs in pid.py to implement the PID controller.

Once done, try running the script to see if the vehicle can maintain a depth of 0.5 meter.

python3 depth_control.py
  1. Can you find a set of PID gains that allows the vehicle to reach a target in a timely manner without overshooting?

Problem 2: Heading Control

In this problem, you will implement a PID controller to control the heading of a simulated underwater vehicle.

control-intro contains a python script called heading_control.py that runs a PID controller to control the heading of the vehicle.

  1. Fix the TODOs in heading_control.py to implement the PID controller.

  2. Does the controller work as expected? What can be done to improve the controller?

  3. Implement the fix and test the controller in heading_control.py. Does it work better?