Lesson 5 · Proportional Control
Lesson 5 · Proportional Control
Teacher mode is on. Toggle it off (bottom-right) to preview the student view.
Bouncing kept the robot inside the circle, but it never actually followed the line. This lesson is the real thing: the robot smoothly tracks the edge of the line by making tiny, constant steering adjustments — the same way you'd steer a car around a gentle curve. It's your first control loop, and one of the most important ideas in the whole course.
Learning Objectives
By the end of this lesson you will be able to:
- Explain a setpoint and why the line's edge (~0.5) is ours
- Compute error as
setpoint − sensor_reading, and read its sign - Turn error into a steering correction with a gain
Kp - Steer continuously with
arcade()inside awhile Trueloop - Tune
Kpby watching the robot and adjusting
Steer while you drive: arcade()
Bounce driving reacted after hitting the line. Following means constantly adjusting so you never leave it — like nudging the wheel around a curve instead of stopping to turn.
For that you need to steer without stopping. arcade(speed, turn) does exactly this
— it sets a forward speed and a steering amount in one non-blocking call:
drivetrain.arcade(speed, turn)
# is the same as:
drivetrain.set_effort(speed + turn, speed - turn)
So arcade(0.3, 0.15) speeds up the left wheel and slows the right — the robot
curves. A positive turn steers one way, negative the other, and zero drives
straight.
With base speed 0.3, what does `arcade(0.3, 0.15)` set the two motors to?
Setpoint and error
The setpoint is the reading we want the sensor to hold. Following the edge of
the line, that's about 0.5 — halfway between white and black. Error is how far
off we are:
error = setpoint − sensor_reading
The sign tells us which way we've drifted; the size tells us how far:
| Where the robot is | reading | error = 0.5 − reading | Meaning |
|---|---|---|---|
| On the edge (perfect) | 0.5 | 0.0 | no correction |
| Drifted onto white | 0.2 | +0.3 | steer toward the line |
| Drifted onto black | 0.8 | −0.3 | steer back off the line |
| Far onto white | 0.1 | +0.4 | steer hard toward the line |
Setpoint is 0.5 and the sensor reads 0.2. What is the error?
From error to steering: the gain Kp
We don't feed raw error to the motors — we scale it by a proportional gain,
Kp, to set how strongly the robot reacts:
correction = error × Kp
With Kp = 0.5, an error of +0.3 gives a correction of +0.15. Then we steer with
that correction:
drivetrain.arcade(base_effort, correction)
Bigger error → bigger correction → sharper steer. When the robot is right on the edge
(error 0), the correction is 0 and it drives straight. Notice there's no
if/else — the math handles left vs. right on its own, through the sign.
If Kp = 0.6 and error = 0.3, what is the correction?
The complete control loop
Every pass: read the sensor, compute error, compute correction, steer. Hundreds of times a second.
from XRPLib.differential_drive import DifferentialDrive
from XRPLib.reflectance import Reflectance
from XRPLib.board import Board
import time
drivetrain = DifferentialDrive.get_default_differential_drive()
reflectance = Reflectance.get_default_reflectance()
board = Board.get_default_board()
setpoint = 0.5 # target: the edge of the line
Kp = 0.5 # proportional gain — tune this!
base_effort = 0.3 # forward speed
board.wait_for_button()
while True:
sensor_value = reflectance.get_left()
error = setpoint - sensor_value
correction = error * Kp
drivetrain.arcade(base_effort, correction)
time.sleep(0.01)
Activity · Tuning Kp
Kp is yours to tune by watching the robot:
- Too high → the robot over-corrects and oscillates, weaving rapidly.
- Too low → it reacts sluggishly and drifts off the line.
- Just right → smooth tracking with small corrections.
Your robot follows the line but weaves back and forth rapidly, never settling. What should you do to Kp?
Print your values while you tune (every 50th pass keeps the console readable):
if loop_count % 50 == 0:
print(f"sensor={sensor_value:.2f} error={error:.2f} correction={correction:.2f}")
Real-world connections
Proportional control (and its bigger sibling, PID) runs an enormous amount of the physical world:
Cruise control
The further you are below the set speed, the harder it presses the throttle — error × gain.
Drone stabilization
Drones hold level by constantly correcting in proportion to how far they've tilted.
Lane-keeping
Self-driving lane assist steers in proportion to how far the car has drifted from center.
Wrap-up
- What's the setpoint for edge-following, and why? (~0.5 — the boundary between white and black.)
- What do the sign and size of the error each tell you? (Sign = which way to steer; size = how hard.)
- The robot oscillates — too high or too low
Kp? (Too high; decrease it.)