Introduction: How to Lock a Servo/Motor/Relay

About: We're an ambitious team for developing STEM education by Arduino and Raspberry Pi learning kits as well as robots and aircraft models/drones. Happy to bring you more fun projects and works. Welcome to visit ou…

In our everyday life, we may enter and exit places through this and that door. Some with lock, some without. And some, with a password lock. Enter the right word, you're permitted to go through. But, like in the movie, if you enter a wrong number, arrows will shoot out, alarm will sound aloud, and yes, you'll get caught. Just kidding! We all know in general situations, it will just happen that you won't be able to enter through the door. So here I will make a simple experiment about how to start the servo by this lock of Arduino. The servo can also be replaced with a motor relay or stepper motor.

Step 1: Prepare the Materials

SunFounder Mars/Arduino Uno board - http://bit.ly/2tkaMba

4x4 keypad - http://bit.ly/2tu3x0s

Servo - http://bit.ly/2sqFjEA

Breadboard (with wire) - http://bit.ly/2slvfrB

2 x LED (one red, one green)

2 x Resistor (220Ohm, to protect the LED)

Several jumper wires and Dupont wires

Type-C USB cable

Step 2: Make Clear the Key Values

Check the internal key connection which will be needed later on in the coding.

PS: Detailed information about using this keypad can be found on: http://wiki.sunfounder.cc/index.php?title=4X4_Matrix_Keypad_Module

Step 3: Wire Up the Devices

  1. Wire the keypad to the Mars board: pin X1-X4 and Y1-Y4 to pin 6-9 and 2-5 respectively.
  2. Then the servo to the board: black wire to GND, red to 5V, and brown to pin 10.
  3. Next the LEDs: for each LED, first connect a 220 Ohm resistor to anode, then the cathode to GND. Green one's cathode to pin 11 of the Mars, and red LED to pin 12.

So all the wiring is done!

Step 4: Program the Mars

Write the program, plug in the USB cable, burn the code to the Mars board. After upload is done, open the Serial Monitor.

Remember to inlcude the library below:

/*
|| || @file Keypad.h || @version 3.1 || @author Mark Stanley, Alexander Brevig || @contact mstanley@technologist.com, alexanderbrevig@gmail.com || || @description || | This library provides a simple interface for using matrix || | keypads. It supports multiple keypresses while maintaining || | backwards compatibility with the old single key library. || | It also supports user selectable pins and definable keymaps. || # || || @license || | This library is free software; you can redistribute it and/or || | modify it under the terms of the GNU Lesser General Public || | License as published by the Free Software Foundation; version || | 2.1 of the License. || | || | This library is distributed in the hope that it will be useful, || | but WITHOUT ANY WARRANTY; without even the implied warranty of || | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU || | Lesser General Public License for more details. || | || | You should have received a copy of the GNU Lesser General Public || | License along with this library; if not, write to the Free Software || | Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA || # || */

#ifndef KEYPAD_H #define KEYPAD_H

#include "utility/Key.h"

// Arduino versioning. #if defined(ARDUINO) && ARDUINO >= 100 #include "Arduino.h" #else #include "WProgram.h" #endif

// bperrybap - Thanks for a well reasoned argument and the following macro(s). // See http://arduino.cc/forum/index.php/topic,142041.msg1069480.html#msg1069480 #ifndef INPUT_PULLUP #warning "Using pinMode() INPUT_PULLUP AVR emulation" #define INPUT_PULLUP 0x2 #define pinMode(_pin, _mode) _mypinMode(_pin, _mode) #define _mypinMode(_pin, _mode) \ do { \ if(_mode == INPUT_PULLUP) \ pinMode(_pin, INPUT); \ digitalWrite(_pin, 1); \ if(_mode != INPUT_PULLUP) \ pinMode(_pin, _mode); \ }while(0) #endif

#define OPEN LOW #define CLOSED HIGH

typedef char KeypadEvent; typedef unsigned int uint; typedef unsigned long ulong;

// Made changes according to this post http://arduino.cc/forum/index.php?topic=58337.0 // by Nick Gammon. Thanks for the input Nick. It actually saved 78 bytes for me. :) typedef struct { byte rows; byte columns; } KeypadSize;

#define LIST_MAX 10 // Max number of keys on the active list. #define MAPSIZE 10 // MAPSIZE is the number of rows (times 16 columns) #define makeKeymap(x) ((char*)x)

//class Keypad : public Key, public HAL_obj { class Keypad : public Key { public:

Keypad(char *userKeymap, byte *row, byte *col, byte numRows, byte numCols);

virtual void pin_mode(byte pinNum, byte mode) { pinMode(pinNum, mode); } virtual void pin_write(byte pinNum, boolean level) { digitalWrite(pinNum, level); } virtual int pin_read(byte pinNum) { return digitalRead(pinNum); }

uint bitMap[MAPSIZE]; // 10 row x 16 column array of bits. Except Due which has 32 columns. Key key[LIST_MAX]; unsigned long holdTimer;

char getKey(); bool getKeys(); KeyState getState(); void begin(char *userKeymap); bool isPressed(char keyChar); void setDebounceTime(uint); void setHoldTime(uint); void addEventListener(void (*listener)(char)); int findInList(char keyChar); int findInList(int keyCode); char waitForKey(); bool keyStateChanged(); byte numKeys();

private: unsigned long startTime; char *keymap; byte *rowPins; byte *columnPins; KeypadSize sizeKpd; uint debounceTime; uint holdTime; bool single_key;

void scanKeys(); bool updateList(); void nextKeyState(byte n, boolean button); void transitionTo(byte n, KeyState nextState); void (*keypadEventListener)(char); };

#endif

/* || @changelog || | 3.1 2013-01-15 - Mark Stanley : Fixed missing RELEASED & IDLE status when using a single key. || | 3.0 2012-07-12 - Mark Stanley : Made library multi-keypress by default. (Backwards compatible) || | 3.0 2012-07-12 - Mark Stanley : Modified pin functions to support Keypad_I2C || | 3.0 2012-07-12 - Stanley & Young : Removed static variables. Fix for multiple keypad objects. || | 3.0 2012-07-12 - Mark Stanley : Fixed bug that caused shorted pins when pressing multiple keys. || | 2.0 2011-12-29 - Mark Stanley : Added waitForKey(). || | 2.0 2011-12-23 - Mark Stanley : Added the public function keyStateChanged(). || | 2.0 2011-12-23 - Mark Stanley : Added the private function scanKeys(). || | 2.0 2011-12-23 - Mark Stanley : Moved the Finite State Machine into the function getKeyState(). || | 2.0 2011-12-23 - Mark Stanley : Removed the member variable lastUdate. Not needed after rewrite. || | 1.8 2011-11-21 - Mark Stanley : Added test to determine which header file to compile, || | WProgram.h or Arduino.h. || | 1.8 2009-07-08 - Alexander Brevig : No longer uses arrays || | 1.7 2009-06-18 - Alexander Brevig : This library is a Finite State Machine every time a state changes || | the keypadEventListener will trigger, if set || | 1.7 2009-06-18 - Alexander Brevig : Added setDebounceTime setHoldTime specifies the amount of || | microseconds before a HOLD state triggers || | 1.7 2009-06-18 - Alexander Brevig : Added transitionTo || | 1.6 2009-06-15 - Alexander Brevig : Added getState() and state variable || | 1.5 2009-05-19 - Alexander Brevig : Added setHoldTime() || | 1.4 2009-05-15 - Alexander Brevig : Added addEventListener || | 1.3 2009-05-12 - Alexander Brevig : Added lastUdate, in order to do simple debouncing || | 1.2 2009-05-09 - Alexander Brevig : Changed getKey() || | 1.1 2009-04-28 - Alexander Brevig : Modified API, and made variables private || | 1.0 2007-XX-XX - Mark Stanley : Initial Release || # */

Here is the code:

<p>/*******************************************************<br>   name:Password Lock
   function: the I2C LCD1602 will display "Welcome!" after power on.
   At this point, the indicator LED on the relay keeps off.
   When you press "*" key, it will prompt "Input Your Code:". If you enter “123456” and press “#” key to confirm,
   the indicator LED on the relay module will light up. The I2C LCD1602 will display "Input Correctly" "Please Come In".
   Two seconds later, "Welcome!"
 *********************************************************/
//Email:support@sunfounder.com
//Website:www.sunfounder.com</p><p>#include 
#include  //use the servo 
Servo myservo; //Declare the servo</p><p>const byte ROWS = 4; //four rows
const byte COLS = 4; //four columns
//define the cymbols on the buttons of the keypads
char hexaKeys[ROWS][COLS] =
{
  { '1', '2', '3', '4'  },
  { '5', '6', '7', '8'  },
  { '9', 'A', 'B', 'C'  },
  { 'D', '*', '0', '#'  }
};
//行
byte rowPins[ROWS] = { 2, 3, 4, 5 };
//列
byte colPins[COLS] = { 6, 7, 8, 9 };</p><p>int pos = 0;
char secretCode[6] = { '1', '2', '3', '4', '5', '6'};
char inputCode[6] = { '0', '0', '0', '0', '0', '0'};</p><p>//initialize an instance of class NewKeypad
Keypad customKeypad = Keypad( makeKeymap(hexaKeys), rowPins, colPins, ROWS, COLS);</p><p>void setup()
{</p><p>  Serial.begin(9600);
  delay(2000);
  pinMode(11, OUTPUT);  //绿灯
  pinMode(12, OUTPUT);  //绿灯
  myservo.attach(10); //舵机digital pin 10</p><p>}</p><p>void loop()
{
  readKey();
}</p><p>void readKey()
{
  int correct = 0;
  int i;
  char customKey = customKeypad.getKey();//get the key value</p><p>  if (customKey)
  {</p><p>    switch (customKey)
    {
      case '*': //if press in "*" ,then print "Input Your Code:"
        pos = 0;
        Serial.println("Input Your Code: ");
        break;
      case '#':  //if press in "#" ,then see the  password whether "1 2 3 4 5 6"
        for (i = 0; i < 6; i++)
        {
          if (inputCode[i] == secretCode[i])
          {
            correct ++;
          }
        }
        if (correct == 6) //if it right
        {
          Serial.println("Input correctly!");
          digitalWrite(11, HIGH); //relay connected
          digitalWrite(12, LOW);
          for (int i = 0; i < 120; i++)
          {
            myservo.write(i);
            delay(10);
          }
          for (int i = 120; i > 0; i--)
          {
            myservo.write(i);
            delay(10);
          }
          for (int i = 0; i < 120; i++)
          {
            myservo.write(i);
            delay(10);
          }
          for (int i = 120; i > 0; i--)
          {
            myservo.write(i);
            delay(10);
          }
        }
        else
        {
          Serial.println("Input Error!");
          digitalWrite(12, HIGH);
          digitalWrite(11, LOW);
        }
        break;
      default:
        inputCode[pos] = customKey;
        Serial.println(inputCode[pos]);
        pos ++;</p><p>    }
  }
}</p>

Step 5: Try the Password!

Then on the keypad, press * to start input, the correct password as you set in the code, and at last #. All the entered value will be shown in the serial monitor window.

You can see the green LED light up and the servo start to spin for a while.

If a wrong psw is entered, BOOM! Er, just kidding…unlike in the movie which may be alarm sounding loud security rushing toward you, here, just the red LED lights up.