Skip to content

Instantly share code, notes, and snippets.

@jpwsutton
Created June 4, 2017 13:44
Show Gist options
  • Star 11 You must be signed in to star a gist
  • Fork 4 You must be signed in to fork a gist
  • Save jpwsutton/8b36af5809d1938ee3ebe541c4d26606 to your computer and use it in GitHub Desktop.
Save jpwsutton/8b36af5809d1938ee3ebe541c4d26606 to your computer and use it in GitHub Desktop.
MQTT Wemos Button
/***************************************************
MQTT Button on Wemos
James Sutton 2017 - jsutton.co.uk
****************************************************/
#include <ESP8266WiFi.h>
#include "Adafruit_MQTT.h"
#include "Adafruit_MQTT_Client.h"
/************************* WiFi Access Point *********************************/
#define WLAN_SSID "WIFI SSID"
#define WLAN_PASS "WIFI KEY"
/************************* MQTT Setup *********************************/
#define MQTT_SERVER "__SERVER__"
#define MQTT_SERVERPORT 1883 // use 8883 for SSL
#define MQTT_USERNAME "__USERNAME__"
#define MQTT_PASSWORD "__PASSWORD__"
/************************* Button Config *********************************/
const int buttonPin = D5;
/************ Global State (you don't need to change this!) ******************/
// Create an ESP8266 WiFiClient class to connect to the MQTT server.
WiFiClient client;
// or... use WiFiFlientSecure for SSL
//WiFiClientSecure client;
// Setup the MQTT client class by passing in the WiFi client and MQTT server and login details.
Adafruit_MQTT_Client mqtt(&client, MQTT_SERVER, MQTT_SERVERPORT, MQTT_USERNAME, MQTT_PASSWORD);
int buttonState; // the current reading from the input pin
int lastButtonState = LOW; // the previous reading from the input pin
// the following variables are unsigned long's because the time, measured in miliseconds,
// will quickly become a bigger number than can be stored in an int.
unsigned long lastDebounceTime = 0; // the last time the output pin was toggled
unsigned long debounceDelay = 50; // the debounce time; increase if the output flickers
/****************************** Feeds ***************************************/
// Setup a feed for publishing.
Adafruit_MQTT_Publish buttonPub = Adafruit_MQTT_Publish(&mqtt, MQTT_USERNAME "/buttonPub");
/*************************** Sketch Code ************************************/
// Bug workaround for Arduino 1.6.6, it seems to need a function declaration
// for some reason (only affects ESP8266, likely an arduino-builder bug).
void MQTT_connect();
void setup() {
pinMode(buttonPin, INPUT);
Serial.begin(115200);
delay(10);
Serial.println(F("MQTT Emergency Button"));
// Connect to WiFi access point.
Serial.println(); Serial.println();
Serial.print("Connecting to ");
Serial.println(WLAN_SSID);
WiFi.begin(WLAN_SSID, WLAN_PASS);
while (WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println();
Serial.println("WiFi connected");
Serial.println("IP address: "); Serial.println(WiFi.localIP());
// Send Hello World Notification
MQTT_connect();
// Now we can publish stuff!
Serial.print(F("\nSending Hello!"));
Serial.print("...");
if (! buttonPub.publish("Hello")) {
Serial.println(F("Failed"));
} else {
Serial.println(F("OK!"));
}
}
void loop() {
// read the state of the switch into a local variable:
int reading = digitalRead(buttonPin);
// check to see if you just pressed the button
// (i.e. the input went from LOW to HIGH), and you've waited
// long enough since the last press to ignore any noise:
// If the switch changed, due to noise or pressing:
if (reading != lastButtonState) {
// reset the debouncing timer
lastDebounceTime = millis();
}
if ((millis() - lastDebounceTime) > debounceDelay) {
// whatever the reading is at, it's been there for longer
// than the debounce delay, so take it as the actual current state:
// if the button state has changed:
if (reading != buttonState) {
buttonState = reading;
// only toggle the LED if the new button state is HIGH
if (buttonState == HIGH) {
sendUpdate();
}
}
}
// save the reading. Next time through the loop,
// it'll be the lastButtonState:
lastButtonState = reading;
}
void sendUpdate() {
// Ensure the connection to the MQTT server is alive (this will make the first
// connection and automatically reconnect when disconnected). See the MQTT_connect
// function definition further below.
MQTT_connect();
// Now we can publish stuff!
Serial.print(F("\nSending button press!"));
Serial.print("...");
if (! buttonPub.publish(1)) {
Serial.println(F("Failed"));
} else {
Serial.println(F("OK!"));
}
// ping the server to keep the mqtt connection alive
// NOT required if you are publishing once every KEEPALIVE seconds
/*
if(! mqtt.ping()) {
mqtt.disconnect();
}
*/
}
// Function to connect and reconnect as necessary to the MQTT server.
// Should be called in the loop function and it will take care if connecting.
void MQTT_connect() {
int8_t ret;
// Stop if already connected.
if (mqtt.connected()) {
return;
}
Serial.print("Connecting to MQTT... ");
uint8_t retries = 3;
while ((ret = mqtt.connect()) != 0) { // connect will return 0 for connected
Serial.println(mqtt.connectErrorString(ret));
Serial.println("Retrying MQTT connection in 5 seconds...");
mqtt.disconnect();
delay(5000); // wait 5 seconds
retries--;
if (retries == 0) {
// basically die and wait for WDT to reset me
while (1);
}
}
Serial.println("MQTT Connected!");
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment