K Gray
Published © MIT

Automated Driveway Gate(s) (LPR)

This tutorial is about making an automated gate for your driveway for (relatively) cheap with ESP8266, Arduino, Raspberry Pi and Blynk!

IntermediateFull instructions provided5 hours3,641

Things used in this project

Hardware components

Linear Actuator
×2
ESP8266 D1-MINI
×1
Arduino UNO
Arduino UNO
×1
Motor Driver
RZ7886 for PCB Link: https://lcsc.com/product-detail/Motor-Drivers_RZ-Wuxi-Smart-Microelectronics-RZ7886_C128852.html
×1
Waterproof Enclosure
×1
Power Supply
×1
Jumper wires (generic)
Jumper wires (generic)
×1
Wire, Wrapping Wire
Wire, Wrapping Wire
×1
Linear Regulator (7805)
Linear Regulator (7805)
×1
Custom PCB
Custom PCB
Optional Link: https://oshwlab.com/KGray7/driveway-v10-redo
×1

Software apps and online services

Blynk
Blynk
Adafruit
Maker service
IFTTT Maker service
Optional
Clicksend
Optional

Hand tools and fabrication machines

Soldering iron (generic)
Soldering iron (generic)
Solder Wire, Lead Free
Solder Wire, Lead Free
Multitool, Screwdriver
Multitool, Screwdriver
Drill / Driver, Cordless
Drill / Driver, Cordless
Wood Boring Bit

Story

Read more

Schematics

Automated Driveway Gate Schematic

Code

Driveway Gate

C/C++
#define BLYNK_PRINT Serial

#include "settings.h"
#include <ESP8266WiFi.h>
#include <ESP8266WebServer.h>
#include <BlynkSimpleEsp8266.h>
#include <math.h>

char auth[] = BLYNK_AUTH_TOKEN;

int timer = 0;
int button;
int emergency;
int setting;
int delayAMOUNT;
int gpsSelect;
int distanceSelect;
int comingHome;
int openTest;
int closeTest;
float GPSLat;
float GPSLong;

float dist_calc=0;
float dist_calc2=0;
float diflat=0;
float diflon=0;

BLYNK_CONNECTED() {
  Blynk.syncAll();
  Serial.println("Syncing...");
  delay(2000);
}
BLYNK_WRITE(V0){
  button = param.asInt();
}
BLYNK_WRITE(V1){
  emergency = param.asInt();
}
BLYNK_WRITE(V2){
  setting = param.asInt();
  if (setting == 1) {
    Mode = "automatic";
  }
  else if (setting == 0) {
    Mode = "button";
  }
}
BLYNK_WRITE(V3){
  gateOpenAmount = param.asInt();
}

BLYNK_WRITE(V4){
  delayAMOUNT = param.asInt();
}
BLYNK_WRITE(V5){
  GpsParam gps(param);
  GPSLat = gps.getLat();
  GPSLong = gps.getLon();
}
WidgetLED led(V6);
BLYNK_WRITE(V8){
  gpsSelect = param.asInt();
}
BLYNK_WRITE(V9){
  distanceSelect = param.asInt();
}
BLYNK_WRITE(V10){
  comingHome = param.asInt();
}
BLYNK_WRITE(V12){
  openTest = param.asInt();
}
BLYNK_WRITE(V13){
  closeTest = param.asInt();
}

void setup() {
  Serial.begin(9600);
  if (gateNumber == 1){
    pinMode(a1, OUTPUT);
    pinMode(a2, OUTPUT);
  }
  else if (gateNumber == 2){
    pinMode(a1, OUTPUT);
    pinMode(a2, OUTPUT);
    pinMode(b1, OUTPUT);
    pinMode(b2, OUTPUT);
  }
  pinMode(emergencyButton, INPUT_PULLUP);
  Blynk.begin(BLYNK_AUTH_TOKEN,WIFI_SSID,WIFI_PASS);
  led.on();
  led.setColor(BLYNK_RED);
}

void loop() {
  Blynk.virtualWrite(V11, WiFi.RSSI());
  if (emergencyButton == LOW){
    Serial.println("Emergency Button!");
    Blynk.notify("Emergency Button on Gates was just Pressed!!!");
    gates();
  }
  if (openTest == 1){
    openGate();
  }
  if (closeTest == 1){
    closeGate();
  }
  if (button == 1){
    Serial.println("Button pressed.");
    gates();
  }
  if (emergency == 1){
    Serial.println("M");
    led.setColor(BLYNK_YELLOW);
    manual();
    delay(delayAMOUNT*1000);
    led.setColor(BLYNK_RED);
  }
  if (gpsSelect != 1){
    Blynk.virtualWrite(V7,calcDist(GPSLat, GPSLong, YOUR_LAT, YOUR_LONG));
    if (comingHome == 1){
      Serial.println(calcDist(GPSLat, GPSLong, YOUR_LAT, YOUR_LONG));
      if (calcDist(GPSLat, GPSLong, YOUR_LAT, YOUR_LONG) < distanceSelect){
        Serial.println("GPS triggered!");
        opengates();
      }
    }
  }
  Blynk.run();
}

void gates(){
  Serial.println("Got Mail!");
  if (Mode == "automatic"){
    Serial.println("Mode = Automatic");
    Serial.println("Opening gate...");
    led.setColor(BLYNK_BLUE);
    openGate();
    waitForGate();
    allStop();
    led.setColor(BLYNK_GREEN);
    Serial.println("Open.");
    Serial.println("Waiting...");
    delay(gateOpenAmount*1000);
    Serial.println("Closing gate...");
    led.setColor(BLYNK_BLUE);
    closeGate();
    waitForGate();
    allStop();
    led.setColor(BLYNK_RED);
    Serial.println("Closed.");
  }
  else if(Mode == "button"){
    Serial.println("Mode = Button");
    if (timer == 0){
      Serial.println("Openning gate...");
      led.setColor(BLYNK_BLUE);
      openGate();
      waitForGate();
      allStop();
      led.setColor(BLYNK_GREEN);
      Serial.println("Open.");
      timer = 1;
    }
    else if(timer == 1){
      Serial.println("Closing gate...");
      led.setColor(BLYNK_BLUE);
      closeGate();
      waitForGate();
      allStop();
      led.setColor(BLYNK_RED);
      Serial.println("Closed.");
      timer = 0;
    }
  }
}

void openGate(){
  if (gateDirection == 1){
    if (gateNumber == 1){
      digitalWrite(a1, HIGH);
      digitalWrite(a2, LOW);
    }
    else if (gateNumber == 2){
      digitalWrite(a1, HIGH);
      digitalWrite(a2, LOW);
      digitalWrite(b1, HIGH);
      digitalWrite(b2, LOW);
    }
  }
  else if (gateDirection == 2){
    if (gateNumber == 1){
      digitalWrite(a1, LOW);
      digitalWrite(a2, HIGH);
    }
    else if (gateNumber == 2){
      digitalWrite(a1, LOW);
      digitalWrite(a2, HIGH);
      digitalWrite(b1, LOW);
      digitalWrite(b2, HIGH);
    }
  }
}

void closeGate(){
  if (gateDirection == 1){
    if (gateNumber == 1){
      digitalWrite(a1, LOW);
      digitalWrite(a2, HIGH);
    }
    else if (gateNumber == 2){
      digitalWrite(a1, LOW);
      digitalWrite(a2, HIGH);
      digitalWrite(b1, LOW);
      digitalWrite(b2, HIGH);
    }
  }
  else if (gateDirection == 2){
    if (gateNumber == 1){
      digitalWrite(a1, HIGH);
      digitalWrite(a2, LOW);
    }
    else if (gateNumber == 2){
      digitalWrite(a1, HIGH);
      digitalWrite(a2, LOW);
      digitalWrite(b1, HIGH);
      digitalWrite(b2, LOW);
    }
  }
}

void allStop() {
  if (gateNumber == 1){
    digitalWrite(a1, LOW);
    digitalWrite(a2, LOW);
  }
  else if (gateNumber == 2){
    digitalWrite(a1, LOW);
    digitalWrite(a2, LOW);
    digitalWrite(b1, LOW);
    digitalWrite(b2, LOW);
  }
}

void manual() {
  if (gateNumber == 1){
    digitalWrite(a1, HIGH);
    digitalWrite(a2, HIGH);
  }
  else if (gateNumber == 2){
    digitalWrite(a1, HIGH);
    digitalWrite(a2, HIGH);
    digitalWrite(b1, HIGH);
    digitalWrite(b2, HIGH);
  }
}

void waitForGate() {
  delay((inchesPerSec*(maxActuatorStroke/percentOfMaxStroke))*1000);
}

void opengates(){
  Serial.println("Mode = Button");
  Serial.println("Openning gate...");
  led.setColor(BLYNK_BLUE);
  openGate();
  waitForGate();
  allStop();
  led.setColor(BLYNK_GREEN);
  Serial.println("Open.");
  timer = 1;
}


float calcDist(float CurrentLatitude, float CurrentLongitude, float SavedLatitude, float SavedLongitude)
{
// HaverSine version
    const float Deg2Rad = 0.01745329252;               // (PI/180)  0.017453293, 0.0174532925
    //const double EarthRadius = 6372.795;              //6372.7976 In Kilo meters, will scale to other values
    const float EarthRadius = 20908120.1;              // In feet  20908128.6
    float DeltaLatitude, DeltaLongitude, a, Distance;

    // degrees to radians
    CurrentLatitude = (CurrentLatitude + 180) * Deg2Rad;     // Remove negative offset (0-360), convert to RADS
    CurrentLongitude = (CurrentLongitude + 180) * Deg2Rad;
    SavedLatitude = (SavedLatitude + 180) * Deg2Rad;
    SavedLongitude = (SavedLongitude + 180) * Deg2Rad;

    DeltaLatitude = SavedLatitude - CurrentLatitude;
    DeltaLongitude = SavedLongitude - CurrentLongitude;

    a =(sin(DeltaLatitude/2) * sin(DeltaLatitude/2)) + cos(CurrentLatitude) * cos(SavedLatitude) * (sin(DeltaLongitude/2) * sin(DeltaLongitude/2));
    Distance = EarthRadius * (2 * atan2(sqrt(a),sqrt(1-a)));
    Blynk.virtualWrite(V7, Distance);
    return(Distance);
}

settings.h

C/C++
#define emergencyButton 14

//blynk
#define BLYNK_AUTH_TOKEN "your_auth"
#define BLYNK_GREEN     "#23C48E"
#define BLYNK_RED       "#D3435C"
#define BLYNK_YELLOW    "#ED9D00"
#define BLYNK_BLUE      "#04C0F8"
#define YOUR_LAT        40.677364  //New York City
#define YOUR_LONG       -73.998944

//WiFi
char WIFI_SSID[] = "Apple Network 85064d";
char WIFI_PASS[] = "12344321";

//GATE
String Mode = "button";      //automatic or button
#define gateNumber 2          //how many gates; 1 or 2
int gateOpenAmount = 10;     //only for automatic mode, seconds
#define gateDirection 1       //1 or 2

//linear actuator
#define inchesPerSec .39      //inches per sec of linear actuator
#define maxActuatorStroke 12  //max stroke of linear actuator
#define percentOfMaxStroke .21 //.2 //0 through 1
#define a1 2                  //first linear actuator
#define a2 0                  //first linear actuator
#define b1 4                  //second linear actuator
#define b2 5                  //second linear actuator

Driveway Gate Code on Github

Credits

K Gray

K Gray

23 projects • 23 followers
I love making things out of electronic components, coding in python and C++, designing PCBs and lots more.

Comments