Fun with Arduino

Reflex

Luis Martín

The Arduino platform is not limited just to serious home automation projects. In this article, we show you how easy it is to make something fun.

The great versatility Arduino [1] allows it to be used for anything from a sensory node, to a smart kitchen automation controller, to the brain of a small remote control car you can steer with a hand gesture. However, as I was told as a child, everything has its time and place. Sometimes, one must be serious to convey responsibility, but in other situations, fun should be the name of the game because, you know, life is short.

The project I am sharing with you this issue allows you to have a good time, use your knowledge of circuits and electronics, and impress your friends and family with your abilities. This tutorial implements a simple game that involves two players pressing buttons when an LED flashes. A gauge with a swinging indicator, like a speedometer, indicates which player is winning the battle of reflexes (i.e., who presses their button first most often).

Hardware Design

The project requires two buttons, seven LED diodes, and a servomotor. All of these components should be familiar, except perhaps the servomotor, so I'll begin by providing you with some basic information.

A servomotor, as you can see in Figure 1, is a motor with a controlled output shaft, which means you can position it wherever you want, within its performance range. Servomotors usually have a range of 180 degrees, although some range through 210, or even 360, degrees.

Figure 1: Servomotor used in the assembly.

Servomotors are no more than DC motors with a series of gears that convert speed to torque (force) and a control system that uses a potentiometer that informs you of the position of the servo's shaft at any given time. This control system also responds to signals sent to it to determine the shaft's position.

The signal input into the servomotor is similar, but not identical, to pulse-width modulation [2]; depending on the width of the pulse sent, the servo will be placed in one position or another. Here, the pulse frequencies must be 20ms (50Hz) apart, so the servomotor can interpret them correctly, although they could equally well fall in a range from 10 to 30ms. That is, the servomotor will read the signal input every 20ms, and depending on the duration of the logical 1 (the pulse width from +5V), it will calculate the degrees of movement the servo shaft must take (Figure 2).

Figure 2: Basic servomotor operations.

In the electronic diagram of Figure 3, you can see how the circuit is mounted. A list of the key components make it even clearer:

Programming

If you look at Listing 1 at the end of the article, you'll see that you need to add the servo.h library (line 1). This library saves you the work of having to calculate the duration in milliseconds (ms) of the pulse you send to the servomotor to move it to a specific angle. To use it, you simply create a Servo object – in this case, servo1 (line 3). Next (lines 5-9), you need to set the variables that store the initial position of the servomotor (degrees), as well as the Arduino pin to which the servo connects. Following that, a further two Boolean variables store the button states. Boolean variables can take on only two states: a logical 1 (true) or a logical 0 (false).

Other variables (lines 11-31) initiate program loops, timers, counters, and so on, as well as assign the pins needed for the project.

Now you're ready to move on to the setup() routine, which begins in line 33. The first thing it does is link the servomotor to a pin. In this case, it uses pin 9, which is stored in servoPin (line 6). Next, the program moves the servomotor across its full range of action, from 0 (servo1.write(0)) to 179 degrees (servo1.write(179)), and then moves it to the game's starting point previously defined in the variable degrees.

After checking that everything has been initialized correctly, the program moves to the main loop(). The random(<min>, <max>) instruction (line 56) generates pseudo-random numbers from 0 to 99, causing the players' LEDs to light up unpredictably. The millis() instruction (line 57) provides the time the program has been active in milliseconds. It will overflow and return to zero approximately 50 days after powering up the board.

The program also checks in each loop to see whether the LED frequency has reached an absurd level (e.g., an LED takes <50ms to switch off). If this is the case, it ends the game and calls the Winner function (lines 62-65). In each cycle, 4ms is subtracted from the time that LEDs remain on (line 69) and 10ms from the LEDs that are already on (line 68), making the game more hectic.

The main part of the program is the next while loop (line 73), which checks the buttons while the LED is on. So, while the difference between time2 and time is less than the time the LED is on, the program executes time2 = millis() (line 75), which saves the new active time of the board, from which the time stored at the beginning of the main loop is subtracted (lines 73 and 121). This creates a false delay, during which instructions like reading the button can execute. So, if freqLed is 400, until 400ms have passed since the beginning of the loop, it will not exit the while structure, which means the LED stays on and the buttons are checked continuously.

Finally, as an indication of the winner, the program makes the servo wave from side to side (lines 209-223) while the winner's LED lights up and gradually dims. After that, the program restarts.

An Advent calendar during the Holiday season is a lovely tradition, but the calendars on the market are rather ordinary. We describe a Rasp Pi project that lets you create an innovative and unique Advent calendar.