Actuators
Table of Contents
Physical Output
DC motor
Servo motor
Stepper motor
%%html
<iframe src="https://www.youtube.com/embed/Irgz_qy27qc"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Lab 1: 7 Segment
Turn all leds in 7 segment
With 390 ohm resistor
When a pin is LOW, the corresponding LED is on.
const int a = 2;
const int b = 3;
const int c = 4;
const int d = 5;
const int e = 6;
const int f = 7;
const int g = 8;
const int dp = 9;
void setup()
{
pinMode(a, OUTPUT);
pinMode(b, OUTPUT);
pinMode(c, OUTPUT);
pinMode(d, OUTPUT);
pinMode(e, OUTPUT);
pinMode(f, OUTPUT);
pinMode(g, OUTPUT);
pinMode(dp, OUTPUT);
}
void loop()
{
digitalWrite(a, LOW);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, LOW);
digitalWrite(e, LOW);
digitalWrite(f, LOW);
digitalWrite(g, LOW);
digitalWrite(dp, LOW);
delay(1000);
}
Lab 2: 7 Segment LED Counter from 0 to 9
%%html
<iframe src="https://www.youtube.com/embed/f_W370eWKxE"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Naive code
const int a = 2;
const int b = 3;
const int c = 4;
const int d = 5;
const int e = 6;
const int f = 7;
const int g = 8;
void setup()
{
pinMode(a, OUTPUT);
pinMode(b, OUTPUT);
pinMode(c, OUTPUT);
pinMode(d, OUTPUT);
pinMode(e, OUTPUT);
pinMode(f, OUTPUT);
pinMode(g, OUTPUT);
}
void loop()
{
//Display 0
digitalWrite(a, LOW);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, LOW);
digitalWrite(e, LOW);
digitalWrite(f, LOW);
digitalWrite(g, HIGH);
delay(1000);
//Display 1
digitalWrite(a, HIGH);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, HIGH);
digitalWrite(e, HIGH);
digitalWrite(f, HIGH);
digitalWrite(g, HIGH);
delay(1000);
//Display 2
digitalWrite(a, LOW);
digitalWrite(b, LOW);
digitalWrite(c, HIGH);
digitalWrite(d, LOW);
digitalWrite(e, LOW);
digitalWrite(f, HIGH);
digitalWrite(g, LOW);
delay(1000);
//Display 3
digitalWrite(a, LOW);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, LOW);
digitalWrite(e, HIGH);
digitalWrite(f, HIGH);
digitalWrite(g, LOW);
delay(1000);
//Display 4
digitalWrite(a, HIGH);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, HIGH);
digitalWrite(e, HIGH);
digitalWrite(f, LOW);
digitalWrite(g, LOW);
delay(1000);
//Display 5
digitalWrite(a, LOW);
digitalWrite(b, HIGH);
digitalWrite(c, LOW);
digitalWrite(d, LOW);
digitalWrite(e, HIGH);
digitalWrite(f, LOW);
digitalWrite(g, LOW);
delay(1000);
//Display 6
digitalWrite(a, LOW);
digitalWrite(b, HIGH);
digitalWrite(c, LOW);
digitalWrite(d, LOW);
digitalWrite(e, LOW);
digitalWrite(f, LOW);
digitalWrite(g, LOW);
delay(1000);
//Display 7
digitalWrite(a, LOW);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, HIGH);
digitalWrite(e, HIGH);
digitalWrite(f, HIGH);
digitalWrite(g, HIGH);
delay(1000);
//Display 8
digitalWrite(a, LOW);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, LOW);
digitalWrite(e, LOW);
digitalWrite(f, LOW);
digitalWrite(g, LOW);
delay(1000);
//Display 9
digitalWrite(a, LOW);
digitalWrite(b, LOW);
digitalWrite(c, LOW);
digitalWrite(d, LOW);
digitalWrite(e, HIGH);
digitalWrite(f, LOW);
digitalWrite(g, LOW);
delay(1000);
}
Using 2D array
byte digits[10][7] = {
{0, 0, 0, 0, 0, 0, 1}, // 0
{1, 0, 0, 1, 1, 1, 1}, // 1
{0, 0, 1, 0, 0, 1, 0}, // 2
{0, 0, 0, 0, 1, 1, 0}, // 3
{1, 0, 0, 1, 1, 0, 0}, // 4
{0, 1, 0, 0, 1, 0, 0}, // 5
{0, 1, 0, 0, 0, 0, 0}, // 6
{0, 0, 0, 1, 1, 1, 1}, // 7
{0, 0, 0, 0, 0, 0, 0}, // 8
{0, 0, 0, 1, 1, 0, 0} // 9
};
void displayDigit(int num) {
int pin = 2;
for (int i = 0; i < 7; i++) {
digitalWrite(pin + i, digits[num][i]);
}
}
void setup() {
for (int i = 2; i < 10; i++) {
pinMode(i, OUTPUT);
}
digitalWrite(9, HIGH);
}
void loop() {
for (int i = 0; i < 10; i++) {
delay(1000);
displayDigit(i);
}
}
Lab 3: 7 Segment LED Counter with Buttons
%%html
<iframe src="https://www.youtube.com/embed/0VLL_Gqmwuw"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
#define PLUS 11
#define MINUS 12
int digit = 0;
byte digits[10][7] = {
{0, 0, 0, 0, 0, 0, 1}, // 0
{1, 0, 0, 1, 1, 1, 1}, // 1
{0, 0, 1, 0, 0, 1, 0}, // 2
{0, 0, 0, 0, 1, 1, 0}, // 3
{1, 0, 0, 1, 1, 0, 0}, // 4
{0, 1, 0, 0, 1, 0, 0}, // 5
{0, 1, 0, 0, 0, 0, 0}, // 6
{0, 0, 0, 1, 1, 1, 1}, // 7
{0, 0, 0, 0, 0, 0, 0}, // 8
{0, 0, 0, 1, 1, 0, 0} // 9
};
void displayDigit(int num) {
int pin = 2;
for (int i = 0; i < 7; i++) {
digitalWrite(pin + i, digits[num][i]);
}
}
void setup() {
pinMode(PLUS, INPUT);
pinMode(MINUS, INPUT);
for (int i = 2; i < 10; i++) {
pinMode(i, OUTPUT);
}
digitalWrite(9, HIGH);
}
void loop() {
if (digitalRead(PLUS) == HIGH) {
++digit;
if (digit > 9) {
digit = 0;
}
}
if (digitalRead(MINUS) == HIGH) {
--digit;
if (digit < 0) {
digit = 9;
}
}
displayDigit(digit);
delay(100);
}
LiquidCrystal library
allows you to control LCD displays.Parameters
rs: the number of the Arduino pin that is connected to the RS pin on the LCD
rw: the number of the Arduino pin that is connected to the RW pin on the LCD (optional)
enable: the number of the Arduino pin that is connected to the enable pin on the LCD
d0, d1, d2, d3, d4, d5, d6, d7: the numbers of the Arduino pins that are connected to the corresponding data pins on the LCD. d0, d1, d2, and d3 are optional; if omitted, the LCD will be controlled using only the four data lines (d4, d5, d6, d7).
%%html
<iframe src="https://www.youtube.com/embed/85LvW1QDLLw"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Lab 4: Simple and Static LCD Display
%%html
<iframe src="https://www.youtube.com/embed/OqLmj_BVOVw"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
#include <LiquidCrystal.h>
// initialize the library by providing the nuber of pins to it
LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
void setup() {
lcd.begin(16, 2);
// set cursor position to start of first line on the LCD
lcd.setCursor(0, 0);
//text to print
lcd.print(" 16x2 LCD");
// set cusor position to start of next line
lcd.setCursor(0, 1);
lcd.print(" DISPLAY");
}
void loop() {
}
Lab 5: LCD Counter
%%html
<iframe src="https://www.youtube.com/embed/24v2BrXJApw"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
#include <LiquidCrystal.h>
int cnt = 0;
// initialize the library by providing the nuber of pins to it
LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
void setup() {
lcd.begin(16, 2);
// set cursor position to start of first line on the LCD
lcd.setCursor(0, 0);
//text to print
lcd.print(" COUNTER");
delay(100);
lcd.setCursor(0, 1);
lcd.print(" ");
lcd.print(cnt);
}
void loop() {
cnt = cnt + 1;
delay(1000);
lcd.setCursor(0, 1);
lcd.print(" ");
lcd.print(cnt);
}
Note
Check the below simple game using LCD
%%html
<iframe src="https://www.youtube.com/embed/oX6Z890Zd2A?start=9"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
%%html
<iframe src="https://player.vimeo.com/video/84274150"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Two terminals
when you apply direct current to one terminal and ground the other, the motor spins in one direction.
When you apply current to the other terminal and ground the first terminal, the motor spins in the opposite direction.
Control DC motor
By switching the polarity of the terminals, you can reverse the direction of the motor.
By varying the current supplied to the motor (analog $\rightarrow$ PWM), you vary the speed of the motor.
%%html
<iframe src="https://www.youtube.com/embed/j6D9-GKhAyc"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
The small DC motor, is likely to use more power than an Arduino digital output can handle directly. If we tried to connect the motor straight to an Arduino pin, there is a good chance that it could damage the Arduino. Due to the fact that drawing too much current from the Arduino may damage the circuit, transistors are often used to modulate the current flow.
A small transistor can be used as a switch that uses just a little current from the Arduino digital output to control the much bigger current of the motor.
The transistor that we will be using for the lab may have a slightly different layout from some references, so please be sure to make sure that you have checked the layout of the transistor. Right below is the pin layout of the transistor.
The transistor has three leads. Most of the electricity flows from the Collector to the Emitter, but this will only happen if a small amount is flowing into the Base connection. This small current is supplied by the Arduino digital output.
Water Analogy
1) On (when $V_B$ is high)
2) Off (when $V_B$ is low)
3) Linear flow control (when $V_B$ is PWM)
The diagram below is called a schematic diagram. Like a breadboard layout, it is a way of showing how the parts of an electronic project are connected together.
The pin D3 of the Arduino is connected to the resistor. Just like when using an LED, this limits the current flowing into the transistor through the base.
Diode
There is a diode connected across the connections of the motor. Diodes only allow electricity to flow in one direction (the direction of their arrow).
When you turn the power off to a motor, you get a negative spike of voltage, that can damage your Arduino or the transistor. The diode protects against this, by shorting out any such reverse current from the motor.
Lab 6: How to Spin a DC Motor with the Arduino
%%html
<iframe src="https://www.youtube.com/embed/4EpZKJsYl1o"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
int transistorPin = 3;
void setup() {
pinMode(transistorPin, OUTPUT);
}
void loop() {
digitalWrite(transistorPin, HIGH);
delay(1000);
digitalWrite(transistorPin, LOW);
delay(1000);
}
%%html
<iframe src="https://player.vimeo.com/video/93555504"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Lab 7: DC Motor Speed Control
int transistorPin = 3; // connected to the base of the transistor
int speed = 100;
void setup() {
pinMode(transistorPin, OUTPUT); // set the transistor pin as output:
}
void loop() {
analogWrite(transistorPin, speed); // use that to control the transistor:
}
The rotational direction of a DC motor can be reversed by switching the polarity of the applied DC voltage. However, this is not practical in an electronic control system.
You can use switching arrangement known as an H-bridge, consisting of four switches with the motor in the center.
Below is a diagram of the H-bridge and which pins do what in our example. Included with the diagram is a truth table indicating how the motor will function according to the state of the logic pins (which are set by our Arduino).
The L293NE/SN754410 is a very basic H-bridge. It has two bridges, one on the left side of the chip and one on the right, and can control 2 motors.
%%html
<iframe src="https://player.vimeo.com/video/100357623?portrait=0"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Lab 8: DC Motor Direction Control Using an H-Bridge
https://itp.nyu.edu/physcomp/labs/motors-and-transistors/dc-motor-control-using-an-h-bridge/
Most motors require a higher voltage and higher current draw than this, so you will need an external power supply. Other examples in this lecture use the Arduino's 5V output for simplicity although it is not recommended.
%%html
<iframe src="https://www.youtube.com/embed/uzIj4oR1ws0"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
const int switchPin = 2; // switch input
const int motor1Pin = 3; // H-bridge leg 1 (pin 2, 1A)
const int motor2Pin = 4; // H-bridge leg 2 (pin 7, 2A)
const int enablePin = 9; // H-bridge enable pin
void setup() {
// set the switch as an input:
pinMode(switchPin, INPUT);
// set all the other pins you're using as outputs:
pinMode(motor1Pin, OUTPUT);
pinMode(motor2Pin, OUTPUT);
pinMode(enablePin, OUTPUT);
// set enablePin high so that motor can turn on:
digitalWrite(enablePin, HIGH);
}
void loop() {
// if the switch is high, motor will turn on one direction:
if (digitalRead(switchPin) == HIGH) {
digitalWrite(motor1Pin, LOW); // set leg 1 of the H-bridge low
digitalWrite(motor2Pin, HIGH); // set leg 2 of the H-bridge high
}
// if the switch is low, motor will turn in the other direction:
else {
digitalWrite(motor1Pin, HIGH); // set leg 1 of the H-bridge high
digitalWrite(motor2Pin, LOW); // set leg 2 of the H-bridge low
}
}
The position of the servo motor is set by the length of a pulse. The servo expects to receive a pulse roughly every 20 milliseconds (50 Hz). If that pulse is high for 1 millisecond, then the servo angle will be zero, if it is 1.5 milliseconds, then it will be at its center position and if it is 2 milliseconds it will be at 180 degrees.
A servo is different from regular motors in that it has a position sensor, which allows to postion it precisely to a certain angle.
The 'position sensor' is often a potentiometer mechanically connected to the actuator shaft.
The resistance value of the potentiometer is compared with the desired position by a motor controller. The controller moves the moter until the position is matched.
%%html
<iframe src="https://player.vimeo.com/video/93608912"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
%%html
<iframe src="https://www.youtube.com/embed/qatqVNh9uj4"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Lab 9: Controlling the Position of a Servo
You want to control the position of a servo using an angle. Use the Servo
library distributed with Arduino.
%%html
<iframe src="https://www.youtube.com/embed/r59k-1LGjH8"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
#include <Servo.h>
Servo myservo; // create servo object to control a servo
int angle = 0; // variable to store the servo position
void setup()
{
myservo.attach(9); // attaches the servo on pin 10 to the servo object
}
void loop()
{
for (angle = 0; angle < 180; angle += 1) // goes from 0 degrees to 180 degrees
{ // in steps of 1 degree
myservo.write(angle); // tell servo to go to position in variable 'angle'
delay(20); // waits 20ms between servo commands
}
for (angle = 180; angle >= 1; angle -= 1) // goes from 180 degrees to 0 degrees
{
myservo.write(angle); // tell servo to go to position in variable 'angle'
delay(20); // waits 20ms between servo commands
}
}
Lab 10: Controlling a Servo with a Potentiometer or Sensor
You want to control one or two servos with a potentiometer.
%%html
<iframe src="https://www.youtube.com/embed/wybU2--v7ME"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
#include <Servo.h>
Servo myservo; // create servo object to control a servo
int potpin = 0; // analog pin used to connect the potentiometer
int val; // variable to read the value from the analog pin
void setup() {
myservo.attach(9); // attaches the servo on pin 9 to the servo object
}
void loop() {
val = analogRead(potpin); // reads the value of the potentiometer
val = map(val, 0, 1023, 0, 179); // scale it to use it with the servo
myservo.write(val); // sets position to the scaled value
delay(15); // waits for the servo to get there
}
Advanced Servo
Besides the servo library provided in Arduino, you may control the servo without using the library.
%%html
<iframe src="https://www.youtube.com/embed/BSUqhNZYBxY"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
#define SERVO_MIN_PULSE_WIDTH 544 // microseconds
#define SERVO_MAX_PULSE_WIDTH 2400 // microseconds
#define SERVO_MIN_PULSE_CYCLE 20000 // 20 ms -> 50Hz
unsigned long lCyclePrevTime = 0; // micro sec.
unsigned long lCycleCurrTime = 0; // micro sec.
unsigned long lPulseOnPrevTime = 0; // micro sec.
unsigned int nInput = SERVO_MIN_PULSE_WIDTH;
void setup() {
// put your setup code here, to run once:
// Serial communication set
Serial.begin(9600);
// Pin mode set
pinMode(9, OUTPUT);
digitalWrite(9, LOW);
}
void loop() {
// put your main code here, to run repeatedly:
lCyclePrevTime = micros();
while (1)
{
// Serial input
if (Serial.available())
{
nInput = Serial.parseInt();
if (nInput > 180) nInput = 180;
else if (nInput < 0) nInput = 0;
//
nInput = map(nInput, 0, 180, SERVO_MIN_PULSE_WIDTH, SERVO_MAX_PULSE_WIDTH);
Serial.println(nInput);
}
lCycleCurrTime = micros();
if (lCycleCurrTime - lCyclePrevTime >= SERVO_MIN_PULSE_CYCLE)
{
lCyclePrevTime = lCycleCurrTime;
lPulseOnPrevTime = micros();
digitalWrite(9, HIGH);
while (1)
{
if (micros() - lPulseOnPrevTime >= nInput)
{
digitalWrite(9, LOW);
break;
}
}
}
}
}
Demo: Robotic Hand with Servo Motor and Flexible Sensor
%%html
<iframe src="https://www.youtube.com/embed/qMtHEOxHDGo"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
Online Tutorial: Servo motor and transisitors by Jeremy Blum
%%html
<iframe src="https://www.youtube.com/embed/5bHPKU4ybHY"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
%%html
<iframe src="https://www.youtube.com/embed/PEwpAoLKzVc"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
%%html
<iframe src="https://www.youtube.com/embed/bkqoKWP4Oy4"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
%%html
<iframe src="https://www.youtube.com/embed/3A-pcONMSWI"
width="560" height="315" frameborder="0" allowfullscreen></iframe>
%%javascript
$.getScript('https://kmahelona.github.io/ipython_notebook_goodies/ipython_notebook_toc.js')