Remote AC Appliance Control With ESP8266 NodeMCU Relay

by AKP in Circuits > Arduino

92 Views, 2 Favorites, 0 Comments

Remote AC Appliance Control With ESP8266 NodeMCU Relay

esp8266-relay-module-ac-web-server.png

Employing a relay alongside the ESP8266 presents an excellent method for remotely managing AC household appliances. This guide elucidates the process of controlling a relay module using the ESP8266 NodeMCU. We’ll delve into the functionality of a relay module, the steps to connect it to the ESP8266, and the creation of a web server for remote relay control, accommodating multiple relays as needed.

Supplies

  • ESP8266 NodeMCU CP2102 Amazon
  • 5V One Channel Relay Module Amazon

1, 2, 4, 8, 16 Channels Relay Modules

Relay-1-2-4-8-ch-channel-modules.png

Various relay modules feature differing numbers of channels. These modules are available with one, two, four, eight, and even sixteen channels. The quantity of channels dictates the number of outputs that can be regulated.

Certain relay modules are designed to operate with either 5V or 3.3V to power their electromagnets. Both options are compatible with the ESP8266 – users can utilize either the Vin pin (providing 5V) or the 3.3V pin.

Moreover, some modules include built-in optocouplers, introducing an additional protective “layer” by optically isolating the ESP8266 from the relay circuit.

Relay Pinout

Relay-pinout.png

To illustrate, let’s examine the pinout of a 2-channel relay module. Utilizing a relay module with a different number of channels follows a similar setup.

On the left side of the relay module are two connectors, each featuring three sockets for high-voltage connections. Meanwhile, the pins on the right side, designated for low-voltage, connect to the ESP8266 GPIOs.

Mains Voltage Connections

The depicted relay module exhibits two connectors, each equipped with three sockets: common (

COM), normally closed (NC), and normally open (NO).

  • COM: This is where the current intended for control (mains voltage) is connected.
  • NC (Normally Closed): In this configuration, the relay remains closed by default. The NC and COM pins are linked, allowing current flow unless a signal is sent from the ESP8266 to the relay module, opening the circuit and halting the current flow.
  • NO (Normally Open): In contrast, the normally open configuration entails no connection between the NO and COM pins. Hence, the circuit remains open until a signal from the ESP8266 is sent to close it.

Control Pins

The low-voltage side features a set of four pins and another set of three pins. The first set includes 

VCCandGNDfor powering the module, along with input 1 (IN1) and input 2 (IN2) for controlling the bottom and top relays, respectively.

For relay modules with only one channel, there will be a single IN pin. Conversely, modules with multiple channels will have corresponding IN pins.


The signal sent to the IN pins determines the relay’s activation. The relay triggers when the input drops below approximately 2V, resulting in the following scenarios:

  • Normally Closed configuration (NC):
  • HIGH signal – current is flowing
  • LOW signal – current is not flowing
  • Normally Open configuration (NO):
  • HIGH signal – current is not flowing
  • LOW signal – current is flowing

You should use a normally closed configuration when the current should be flowing most of the times, and you only want to stop it occasionally.

Use a normally open configuration when you want the current to flow occasionally (for example, turn on a lamp occasionally).

Power Supply Selection

The second pin set comprises 

GND,VCC, andJD-VCCpins. TheJD-VCCpin powers the relay’s electromagnet. Notably, the module includes a jumper cap connecting the VCC and JD-VCC pins; while shown as yellow here, yours may differ in color.

With the jumper cap in place, the 

VCCandJD-VCCpins are interconnected. Consequently, the relay electromagnet draws power directly from the ESP8266, eliminating physical isolation between the relay module and the ESP8266 circuits.Removing the jumper cap necessitates an independent power source to energize the relay’s electromagnet through the 

JD-VCCpin. This configuration physically isolates the relays from the ESP8266 via the module’s built-in optocoupler, safeguarding the ESP8266 against electrical spikes.

Connecting a Relay Module to the ESP8266 NodeMCU Board

relay-esp8266-wiring.png

Follow the diagram below to wire the relay module to the ESP8266. The diagram illustrates the connection for a 2-channel relay module; wiring for a different number of channels follows a similar pattern.

Alternatively, you can utilize a 12V power source to operate 12V appliances.

In this instance, we’re controlling a lamp. Since we only intend to illuminate the lamp occasionally, it’s preferable to employ a normally open configuration.

We’re linking the IN1 pin to GPIO 5, though any other suitable GPIO can be utilized. Refer to the ESP8266 GPIO Reference Guide for more options.

Controlling a Relay Module With the ESP8266 NodeMCU – Arduino Sketch

The code for managing a relay with the ESP8266 is as straightforward as handling an LED or any other output. In this example, since we’re utilizing a normally open configuration, we must transmit a LOW signal to enable current flow and a HIGH signal to halt it.

The following code will illuminate your lamp for 10 seconds and then deactivate it for another 10 seconds.

const int relay = 5;

void setup() {
Serial.begin(115200);
pinMode(relay, OUTPUT);
}

void loop() {
// Normally Open configuration, send LOW signal to let current flow
// (if you're usong Normally Closed configuration send HIGH signal)
digitalWrite(relay, LOW);
Serial.println("Current Flowing");
delay(5000);

// Normally Open configuration, send HIGH signal stop current flow
// (if you're usong Normally Closed configuration send LOW signal)
digitalWrite(relay, HIGH);
Serial.println("Current not Flowing");
delay(5000);
}


Control Multiple Relays With ESP8266 NodeMCU Web Server

This section presents a web server example enabling control of numerous relays via a web interface, whether configured as normally open or normally closed. Simply adjust a few lines of code to specify the number of relays and their pin assignments.

// Import required libraries
#include "ESP8266WiFi.h"
#include "ESPAsyncWebServer.h"

// Set to true to define Relay as Normally Open (NO)
#define RELAY_NO true

// Set number of relays
#define NUM_RELAYS 5

// Assign each GPIO to a relay
int relayGPIOs[NUM_RELAYS] = {5, 4, 14, 12, 13};

// Replace with your network credentials
const char* ssid = "REPLACE_WITH_YOUR_SSID";
const char* password = "REPLACE_WITH_YOUR_PASSWORD";

const char* PARAM_INPUT_1 = "relay";
const char* PARAM_INPUT_2 = "state";

// Create AsyncWebServer object on port 80
AsyncWebServer server(80);

const char index_html[] PROGMEM = R"rawliteral(
<!DOCTYPE HTML><html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1">
<style>
html {font-family: Arial; display: inline-block; text-align: center;}
h2 {font-size: 3.0rem;}
p {font-size: 3.0rem;}
body {max-width: 600px; margin:0px auto; padding-bottom: 25px;}
.switch {position: relative; display: inline-block; width: 120px; height: 68px}
.switch input {display: none}
.slider {position: absolute; top: 0; left: 0; right: 0; bottom: 0; background-color: #ccc; border-radius: 34px}
.slider:before {position: absolute; content: ""; height: 52px; width: 52px; left: 8px; bottom: 8px; background-color: #fff; -webkit-transition: .4s; transition: .4s; border-radius: 68px}
input:checked+.slider {background-color: #2196F3}
input:checked+.slider:before {-webkit-transform: translateX(52px); -ms-transform: translateX(52px); transform: translateX(52px)}
</style>
</head>
<body>
<h2>ESP Web Server</h2>
%BUTTONPLACEHOLDER%
<script>function toggleCheckbox(element) {
var xhr = new XMLHttpRequest();
if(element.checked){ xhr.open("GET", "/update?relay="+element.id+"&state=1", true); }
else { xhr.open("GET", "/update?relay="+element.id+"&state=0", true); }
xhr.send();
}</script>
</body>
</html>
)rawliteral";

// Replaces placeholder with button section in your web page
String processor(const String& var){
//Serial.println(var);
if(var == "BUTTONPLACEHOLDER"){
String buttons ="";
for(int i=1; i<=NUM_RELAYS; i++){
String relayStateValue = relayState(i);
buttons+= "<h4>Relay #" + String(i) + " - GPIO " + relayGPIOs[i-1] + "</h4><label class=\"switch\"><input type=\"checkbox\" onchange=\"toggleCheckbox(this)\" id=\"" + String(i) + "\" "+ relayStateValue +"><span class=\"slider\"></span></label>";
}
return buttons;
}
return String();
}

String relayState(int numRelay){
if(RELAY_NO){
if(digitalRead(relayGPIOs[numRelay-1])){
return "";
}
else {
return "checked";
}
}
else {
if(digitalRead(relayGPIOs[numRelay-1])){
return "checked";
}
else {
return "";
}
}
return "";
}

void setup(){
// Serial port for debugging purposes
Serial.begin(115200);

// Set all relays to off when the program starts - if set to Normally Open (NO), the relay is off when you set the relay to HIGH
for(int i=1; i<=NUM_RELAYS; i++){
pinMode(relayGPIOs[i-1], OUTPUT);
if(RELAY_NO){
digitalWrite(relayGPIOs[i-1], HIGH);
}
else{
digitalWrite(relayGPIOs[i-1], LOW);
}
}

// Connect to Wi-Fi
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
Serial.println("Connecting to WiFi..");
}

// Print ESP8266 Local IP Address
Serial.println(WiFi.localIP());

// Route for root / web page
server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){
request->send_P(200, "text/html", index_html, processor);
});

// Send a GET request to <ESP_IP>/update?relay=<inputMessage>&state=<inputMessage2>
server.on("/update", HTTP_GET, [] (AsyncWebServerRequest *request) {
String inputMessage;
String inputParam;
String inputMessage2;
String inputParam2;
// GET input1 value on <ESP_IP>/update?relay=<inputMessage>
if (request->hasParam(PARAM_INPUT_1) & request->hasParam(PARAM_INPUT_2)) {
inputMessage = request->getParam(PARAM_INPUT_1)->value();
inputParam = PARAM_INPUT_1;
inputMessage2 = request->getParam(PARAM_INPUT_2)->value();
inputParam2 = PARAM_INPUT_2;
if(RELAY_NO){
Serial.print("NO ");
digitalWrite(relayGPIOs[inputMessage.toInt()-1], !inputMessage2.toInt());
}
else{
Serial.print("NC ");
digitalWrite(relayGPIOs[inputMessage.toInt()-1], inputMessage2.toInt());
}
}
else {
inputMessage = "No message sent";
inputParam = "none";
}
Serial.println(inputMessage + inputMessage2);
request->send(200, "text/plain", "OK");
});
// Start server
server.begin();
}

void loop() {

}


See Full Article Here