Relay switches a motor: button on 12, relay on 9, on an Arduino Uno
Each press of the button on pin 12 flips a relay, driven from pin 9 through an NPN transistor with a diode across its coil; the relay’s contact runs a DC motor from a battery pack, with an LED to show it is on. The whole build, an Arduino Uno and 10 more parts, runs here in your browser on the firmware below; open it in the editor to change the wiring or the code and run it again.
Teaching? Assign it to your class in one click.
Intermediate About 30 minutes to build and run. Runs in your browser. Free, and no account needed.
The parts retail for about $37. On Mokxi they're free.
What you'll learn
- Relays isolate a load from the board
- A flyback diode across a coil
- Debouncing a button with millis()
- Toggling a state on each press
- Difficulty: Intermediate
- Time: About 30 minutes
- Board: Arduino Uno R3
- Parts: 12
How it works
A relay is a switch worked by a coil. Pin 9 drives a transistor through a 1k resistor, the transistor pulls the relay coil to ground, and the relay's contact joins a separate battery to a DC motor. The Uno never carries the motor's current. A diode across the coil catches the voltage kick when the coil switches off.
The button on pin 12 uses an external 10k pull-up to 5V and joins to ground when pressed.
The sketch waits for the button to hold steady for 10 ms, which is debouncing. Each real press flips the relay, so the motor toggles on and off. A green LED on the relay's second contact also lights when the motor is on.
Parts list
12 parts, plus the jumper wires. They retail for about $37; on Mokxi they're free.
- 1 × Arduino Uno R3In Starter Kit, Claw Machine Kit, Vending Machine Kit.
- 1 × Full-size breadboard
- 1 × PushbuttonIn Starter Kit, Christmas Lights Kit, Logic Lab Kit.
- 1 × Resistor, 10k ΩIn Starter Kit, Claw Machine Kit, Halloween Prop Kit.
- 1 × Resistor, 1k ΩIn Starter Kit, Claw Machine Kit, Halloween Prop Kit.
- 1 × Transistor (NPN or PNP)In LED Cube Kit.
- 1 × DPDT relay
- 1 × DiodeIn Pinball Table Kit.
- 1 × Battery: AA, coin cell, LiPoIn Handheld Console Kit, Laser Sword Kit.
- 1 × DC motor
- 1 × Resistor, 220 ΩIn Starter Kit, Claw Machine Kit, Halloween Prop Kit.
- 1 × LED, greenIn Starter Kit, Halloween Prop Kit, Logic Lab Kit.
Kits that can build it
These 5 starter kits have every part in the circuit. Each kit's page lists what else it can build.
Wiring table
Every connection, pin by pin, read from the circuit itself. Each row joins the pin on the left to the pin on the right, by a jumper wire or a breadboard strip.
| Part and pin | Connects to |
|---|---|
| Pushbutton pin 1a | Arduino Uno R3 pin GND |
| Transistor (NPN or PNP) pin E | Arduino Uno R3 pin GND |
| Battery: AA, coin cell, LiPo pin V- | Arduino Uno R3 pin GND |
| DC motor pin 2 | Arduino Uno R3 pin GND |
| LED, green pin C | Arduino Uno R3 pin GND |
| Pushbutton pin 2a | Arduino Uno R3 pin 12 |
| Resistor, 10k Ω pin 1 | Arduino Uno R3 pin 12 |
| Resistor, 1k Ω pin 1 | Arduino Uno R3 pin 9 |
| Resistor, 10k Ω pin 2 | Arduino Uno R3 pin 5V |
| DPDT relay pin COIL1 | Arduino Uno R3 pin 5V |
| DPDT relay pin COM2 | Arduino Uno R3 pin 5V |
| Diode pin C | Arduino Uno R3 pin 5V |
| Transistor (NPN or PNP) pin B | Resistor, 1k Ω pin 2 |
| DPDT relay pin COIL2 | Transistor (NPN or PNP) pin C |
| Diode pin A | Transistor (NPN or PNP) pin C |
| Battery: AA, coin cell, LiPo pin V+ | DPDT relay pin COM1 |
| DC motor pin 1 | DPDT relay pin NO1 |
| DPDT relay pin NC2 | DPDT relay pin NC1 |
| Resistor, 220 Ω pin 1 | DPDT relay pin NO2 |
| LED, green pin A | Resistor, 220 Ω pin 2 |
The code
The firmware exactly as the editor opens it. Change a line there and press Run: it compiles in the browser.
// A relay switches a motor: press the button to start or stop it.
//
// pin 9 -> 1k -> the NPN transistor's base; emitter -> GND
// 5V -> the relay coil -> the transistor's collector, a diode across the coil
// two AA cells -> the relay's contact -> the motor (and an LED with 220 ohm)
// 10k from 5V -> pin 12; the push button from pin 12 -> GND
//
// The motor has its own battery; the relay's contact is the only thing that
// joins it to the motor, so the board never carries the motor's current. The
// diode catches the kick the coil gives when it is switched off.
//
// The sketch waits for the button to stay put for 10 ms before it believes a
// change, then flips the relay on each press.
const int RELAY = 9;
const int BUTTON = 12;
int buttonState = HIGH;
int lastReading = HIGH;
int relayState = LOW;
unsigned long lastChange = 0;
void setup() {
pinMode(BUTTON, INPUT);
pinMode(RELAY, OUTPUT);
digitalWrite(RELAY, relayState);
Serial.begin(9600);
Serial.println("Mokxi Uno: press the button on pin 12 to start or stop the motor");
}
void loop() {
int reading = digitalRead(BUTTON);
if (reading != lastReading) lastChange = millis();
if (millis() - lastChange > 10 && reading != buttonState) {
buttonState = reading;
if (buttonState == LOW) {
relayState = !relayState;
digitalWrite(RELAY, relayState);
Serial.println(relayState ? "motor on" : "motor off");
}
}
lastReading = reading;
}
Code walkthrough
The key functions of the sketch, and what each one does.
setup sketch.ino
Sets the button as an input and the relay pin as an output. It writes the starting relayState, LOW, so the motor is off, then starts serial at 9600 baud.
void setup() {
pinMode(BUTTON, INPUT);
pinMode(RELAY, OUTPUT);
digitalWrite(RELAY, relayState);
Serial.begin(9600);
Serial.println("Mokxi Uno: press the button on pin 12 to start or stop the motor");
}loop sketch.ino
Reads the button. Whenever the reading changes, it notes the time in lastChange. If the reading has stayed the same for over 10 ms and differs from buttonState, it accepts the change. On a press (LOW) it flips relayState, writes it to the relay pin and prints "motor on" or "motor off".
void loop() {
int reading = digitalRead(BUTTON);
if (reading != lastReading) lastChange = millis();
if (millis() - lastChange > 10 && reading != buttonState) {
buttonState = reading;
if (buttonState == LOW) {
relayState = !relayState;
digitalWrite(RELAY, relayState);
Serial.println(relayState ? "motor on" : "motor off");
}
}
lastReading = reading;
}Troubleshooting
The usual mistakes with this circuit, and the fix for each.
- The relay clicks but the motor does not turn This project
The motor runs from its own battery through the relay contact. Check the battery wiring to COM1 and the motor to NO1. - One press toggles more than once This project
That is bounce. The 10 ms check inloopis there to filter it, so keep it in. - The relay is always on This project
Check the transistor's emitter is on ground and the base resistor goes to pin 9. - The input reads random HIGH and LOW when the button is not pressed. Pushbutton
A floating pin picks up noise. Add a 10 k pull-down or pull-up resistor, or use INPUT_PULLUP and wire the button between the pin and GND. Then pressed reads LOW. - The button seems always pressed, or never changes. Pushbutton
A 4-leg tactile switch has legs joined in pairs. Place it across the breadboard center gap so the pairs sit on different rows. Wired along one side, the legs are already connected. - The LED is dim, burns out, or the pin reads wrong because the resistor value is off. Resistor
Read the color bands again. A 220 ohm to 330 ohm resistor suits a typical LED on 5 V. 10k is a common pull-up or pull-down value. Check with a multimeter if unsure. - A pull-up or pull-down resistor is missing, so the input floats and reads random values. Resistor
Tie the input to 5 V or ground through about 10k. Or use INPUT_PULLUP and wire the switch to ground. - The load never turns on, or is always on, because the legs are in the wrong order. Transistor (NPN or PNP)
Check the pinout in the datasheet for your part. A 2N2222 or BC547 can have emitter, base, collector in a different order. Flat side orientation is easy to get wrong.
Change it and keep it
Open it in the editor, change the circuit or the code, and keep your version in a free account.