Mike MackesNoah Mackes
Published © GPL3+

Garage Door Opener

Open, close and monitor your garage door via the web and openHAB

IntermediateFull instructions provided10 hours10,078
Garage Door Opener

Things used in this project

Hardware components

Adafruit HUZZAH ESP8266 Breakout
Adafruit HUZZAH ESP8266 Breakout
×1
Adafruit Magnetic contact switch (door sensor)
×2
Tolako 5v Relay Module for Arduino
×1
30Pcs 2 Pole 5mm Pitch PCB Mount Screw Terminal Block 8A 250V
×1
Vktech 5pcs 6x8cm Double-Side Prototype PCB Universal Printed Circuit Board
×1
TOOGOO(R) 75 x 3mm Red Green Yellow Assorted Color LED Light Emitting Diodes
×1
Resistor 10k ohm
Resistor 10k ohm
×1
Resistor 330 ohm
Resistor 330 ohm
×2
Generic Premium External Power Supply 5v 1A 2A (1000mA - 2000mA) AC/DC Adapter
×1
22AWG Wire/foot
I used 10 feet of CAT 5 instead.
×30
Pocket Solder- 60/40 Rosin Core 0.031" diameter
Pocket Solder- 60/40 Rosin Core 0.031" diameter
×1
Cable tie mounts
Used to guide contact switch wire down garage door opener track
×6
#6 x 1/2 panhead sheetmetal screw
Screws for case lid
×4
Velco 1" x 1" squares
Used to mount case to garage door opener
×4

Software apps and online services

Arduino IDE
Arduino IDE
openHAB
myOpenHAB

Hand tools and fabrication machines

Adafruit USB to TTL Serial Cable - Debug / Console Cable for Raspberry Pi
Soldering iron (generic)
Soldering iron (generic)
Hot glue gun (generic)
Hot glue gun (generic)
3D Printer (generic)
3D Printer (generic)
Multimeter
wire stripper

Story

Read more

Custom parts and enclosures

Garage Door Opener Case Bottom

Garage Door Opener Sensor Mount Screwdrive

Garage Door Opener Case Top

Schematics

Garage Door Opener Huzzah Schematic

Garage Door Opener Huzzah Schematic

Garage Door Opener Huzzah Schematic

Code

GarageDoor 8266 Controller Code

Arduino
#include <ESP8266WiFi.h>
#include <ESP8266WebServer.h>
#include <ESP8266mDNS.h>

//Replace the values in the next 3 line to match your network
IPAddress ip(192,168,1,50);  //Static IP address for this device.  
IPAddress gw(192,168,1,1);   //Gateway address. IP address of your router
IPAddress sub(255,255,255,0);//Subnet mask for this network 

const String SOFTWARE_VERSION = "1.2";
const char* WIFI_SSID = "YOUR_WIFI_SSID";
const char* WIFI_PASSWORD = "YOUR_WIFI_PASSWORD
const char* DEVICENAME = "garagedoor";  // for this example use garagedoor.local for YOUR_DEVICENAME in the openhab items and rules
const int SENSOR_INFO_LED_PIN = 5;
const int WIFI_INFO_LED_PIN = 2;
const int DEVICE_ACTIVATE_PIN = 4;
const int DEVICE_OPEN_SENSOR_PIN = 12;
const int DEVICE_CLOSE_SENSOR_PIN = 13;
const long ACTIVATE_DURATION = 500;
const long CHECK_WIFI_INTERVAL = 30000;
const long CHECK_SENSORS_INTERVAL = 1000;

unsigned long deviceActivateStart;
unsigned long prevMillisSensors = 0;
unsigned long prevMillisWiFi = 0;
unsigned long currMillis = millis();

MDNSResponder mdns;
ESP8266WebServer server(80);

void setup() {
  Serial.begin(115200);
  pinMode(SENSOR_INFO_LED_PIN, OUTPUT);
  pinMode(WIFI_INFO_LED_PIN, OUTPUT);
  pinMode(DEVICE_ACTIVATE_PIN, OUTPUT);
  digitalWrite(DEVICE_ACTIVATE_PIN, LOW);
  pinMode(DEVICE_OPEN_SENSOR_PIN, INPUT);
  pinMode(DEVICE_CLOSE_SENSOR_PIN,INPUT);
  connectToWiFi();
}

void loop() {
  checkWiFi();
  checkDevicesAndSensors();
  server.handleClient();
}

void checkWiFi(){
  currMillis = millis();
  if (currMillis - prevMillisWiFi >= CHECK_WIFI_INTERVAL)
  {
    Serial.println("Checking WIFI");
    prevMillisWiFi = currMillis;
    if (WiFi.status() != WL_CONNECTED)
      connectToWiFi();
  }
}

void connectToWiFi() {
  WiFi.config(ip, gw, sub);
  WiFi.begin(WIFI_SSID, WIFI_PASSWORD);
  
  Serial.print("Setting up MDNS responder");
  while (!mdns.begin(DEVICENAME)) {
         delay(1000);
         Serial.print(".");
  }
  Serial.println("");
  Serial.println("MDNS responder started");
  
  while (WiFi.status() != WL_CONNECTED) {
    digitalWrite(WIFI_INFO_LED_PIN,HIGH);
    delay(500);
    digitalWrite(WIFI_INFO_LED_PIN,LOW);
    delay(500);
  }
  digitalWrite(WIFI_INFO_LED_PIN,LOW);
  
  Serial.println("");
  Serial.println("WiFi connected");  
  Serial.println("IP address: ");
  Serial.println(WiFi.localIP());
  
  server.on("/", serverOk);
  server.on("/device/status", HTTP_GET, getDeviceStatus);
  server.on("/device/activate", HTTP_POST, activateDevice);
  server.on("/version", HTTP_GET, getVersion);
  server.begin();
}

void checkDevicesAndSensors() {
  checkDevices();
  checkSensors();
}

void checkDevices() {
  currMillis = millis();
  if (digitalRead(DEVICE_ACTIVATE_PIN) == HIGH)
  {
    if (currMillis - deviceActivateStart >= ACTIVATE_DURATION)
    {
      Serial.print("Deactivating currMillis = ");
      Serial.println(currMillis);
      digitalWrite(DEVICE_ACTIVATE_PIN, LOW);
    }
  }
}

void checkSensors() {
  currMillis = millis();
  if (currMillis - prevMillisSensors >= CHECK_SENSORS_INTERVAL)
  {
    Serial.println("Checking Sensors");
    prevMillisSensors = currMillis;
    if (deviceStatus(DEVICE_OPEN_SENSOR_PIN, DEVICE_CLOSE_SENSOR_PIN)== "AJAR")
    {
      if (digitalRead(SENSOR_INFO_LED_PIN) == LOW)
        digitalWrite(SENSOR_INFO_LED_PIN, HIGH); 
    }
    else
      digitalWrite(SENSOR_INFO_LED_PIN, LOW);
  }
}

void getDeviceStatus() {
  digitalWrite(WIFI_INFO_LED_PIN,HIGH);
  server.send(200,"text/plain", deviceStatus(DEVICE_OPEN_SENSOR_PIN, DEVICE_CLOSE_SENSOR_PIN));
  digitalWrite(WIFI_INFO_LED_PIN,LOW);
}

void getVersion() {
  digitalWrite(WIFI_INFO_LED_PIN,HIGH);
  server.send(200,"text/plain", SOFTWARE_VERSION);
  digitalWrite(WIFI_INFO_LED_PIN,LOW);
}

void serverOk() {
  digitalWrite(WIFI_INFO_LED_PIN,HIGH);
  server.send(200,"text/plain","Server Ok...");
  digitalWrite(WIFI_INFO_LED_PIN,LOW);
}

String deviceStatus(int OpenSensor, int CloseSensor) {
  String state = "AJAR";
  if (digitalRead(OpenSensor) == LOW)
    state = "OPEN";
  else if (digitalRead(CloseSensor) == LOW)
    state = "CLOSED";

  Serial.print("Device Status = ");
  Serial.println(state);
return state;
}

void activateDevice()
{
  deviceActivateStart = millis();
  Serial.print("Activating deviceActivateStart = ");
  Serial.println(deviceActivateStart);   
  digitalWrite(DEVICE_ACTIVATE_PIN, HIGH);
  digitalWrite(WIFI_INFO_LED_PIN,HIGH);
  server.send(200,"text/plain", "OK"); 
  digitalWrite(WIFI_INFO_LED_PIN,LOW);
}

openHAB garage door sitemap

Plain text
Sample openHAB sitemap for garage door.

To use it:
Save the file to your openHAB sitemaps directory.
sitemap default label="Main Menu"
{
	Frame label="Home"
	{
			Switch item=DoubleGarageDoor mappings=[ON="Door"]
			Text item=DoubleGarageDoorStatus
  }       
}

openHAB garage door items

Plain text
Sample items file for openHAB.

To use:
Save the file to your openHAB items directory. The name of the file needs to match the name of your site map with the .items extension. Replace "YOUR_DEVICENAME" with the DEVICENAME.local value from the ardunio code..
Switch DoubleGarageDoor "Double Garage Door" <"">  {http=">[ON:POST:http://YOUR_DEVICENAME/device/activate]", autoupdate="false"}
String DoubleGarageDoorStatus "Current Position [%s]" <garagedoor> {http="<[http://YOUR_DEVICENAME/device/status:2000:REGEX((.*?))]"}

openHAB garage door rules

Plain text
This is an example of an openHAB rules file that will notify all of registered devices listed in your my.openhab.org account if the garage door has been left in the OPEN or AJAR position for more than 15 minutes.

To use:
1) Replace "YOUR_DEVICENAME" with the DEVICENAME.local value from the ardunio code and place the file in your openHAB rules directory.
2) Connect your openHAB with my.openHAB service. See: https://my.openhab.org/docs
import org.openhab.model.script.actions.Timer

var Timer DGtimer = null

rule "DoubleGarageDoorRecCmdON"
    when
        Item DoubleGarageDoor received command
    then
        logInfo("DoubleGarageDoor", "Double garage door received command.")
        sendHttpGetRequest("http://YOUR_DEVICENAME/device/status")    
end

rule "DoubleGarageDoorOPEN_AJAR_15"
    when
        System started or
        Item DoubleGarageDoorStatus changed
    then
        if (DoubleGarageDoorStatus.state != "CLOSED") { 
            logInfo("DoubleGarageDoorStatus", "State != CLOSED")
            DGtimer = createTimer(now.plusMinutes(15)) [|
                logInfo("DoubleGarageDoorStatus", "Double garage door has been left AJAR or OPEN for 15 minutes!")
                sendBroadcastNotification("Double garage door has been left AJAR or OPEN for 15 minutes!")
            ]
        } else {
            logInfo("DoubleGarageDoorStatus", "State == CLOSED")
            if(DGtimer != null) {
                DGtimer.cancel
                DGtimer = null
            }
        }
end

Credits

Mike Mackes

Mike Mackes

2 projects • 38 followers
Noah Mackes

Noah Mackes

1 project • 6 followers
High School Student with a passion for engineering and just building stuff. Planning on pursuing a degree and career in Engineering.

Comments