Page 164 - The Unofficial Guide to Lego Mindstorms Robots
P. 164
153
}
}
task heartbeat() {
while (true) {
SendMessage (HEARTBEAT_MESSAGE);
Wait (HEARTBEAT_TIME);
}
}
The main task configur es the inputs on the remote control and starts up the other tasks.
The touchWatcher task is fai rly straightforward. It listens for a touch on either touch sensor. When one is detected, the
remote sends out an IR co mmand to Minerva to go forward or to spin in place. Then the task waits for the touch sensor to be
released and sends a stop command to Minerva.
The call to Wait(10) deserves m ore mention; it's an example of a technique called debouncing. Debouncing is a way of
making touch sensors (and buttons in gener al) work reliably. The basic problem occurs just at the point where you press the
touch sensor enough to make its state change f rom off to on. Tiny motions or electrical variations can cause the touch sensor's
output to switch back and forth very quickly between on and off. This effect is called bounce, and it occurs while you're
press g or releasing the switch, between the steady states of off and on. Bounce can be eliminated with an electronic circuit or
in
by special programming, as I've done here . The call to Wait(10)gives the touch sensor signal a chance to settle down before
touchWatcher starts looking for the rel ease of the touch sensor.
The slider on the remote changes the value of the light sensor. lig htWatcher is the task that monitors the light sensor. If
the sensor value changes from light to da rk, the remote tells Mine rva to release the grabber. A dark-to-light transition causes
the remote to send a grab command to Minerv a.
Just what exactly what "light" and "dark" are is a little tricky to defin e. I had originally hard-coded light values, but then the
remote had to be reprogrammed dependin g on whether I was using it in day light or at night. Instead, the remote uses a scheme
to calibrate itself on the fly. It keeps track o f its minimum and maximum light readings in the minimum and maximum
variables, as shown here:
current = SENSOR_1;
if (current < minimum) minimum = current;
if (current > maximum) maximum = current;
midline = minimum + (maximum - minimum) / 2;
Then lightWatcher calculates the midpo int of the minimum and maximum values. This value is used to determine exactly
what light and dark values cause the remot e to fire commands to Minerva. lightWatcher also keeps track of the last
grabber arm command it sent to avoid unnecessarily sending the same com mand twice.