Fita LED RGB + ESP8266 + MQTT

Olá Pessoal,

Vou compartilhar com voces o código que acabei alterando, já nem lembro mais de onde peguei a base do código, mas fiz diversas modificações para controlar a fita de LED RGB com uma placa ESP8266 e enviar as informações para o Home Assistant por MQTT.

Este projeto ainda não coloquei em prática aqui em casa, pois estou pensando em usar fita de led de 12v. Para este projeto eu utilizei fita de led de 5v e acabei alimentando a fita com os 3.3v do próprio esp.

Precisa de:
1 Placa Esp8266 ( É possível usa ESP01 )
1 Fita de LED RGB de 5v

Ligação:
Alimentação da Fita LED = 3.3v
RED = D1
BLUE = D2
GREEN = D3

O código eu subi para o esp8266 com a IDE do Arduino (Existe um tópico aqui no forum explicando como fazer)

#include <ESP8266WiFi.h>
#include <PubSubClient.h>

#define MQTT_VERSION MQTT_VERSION_3_1_1

// Wifi: SSID and password
const char* WIFI_SSID = "SUA_REDE_WIFI";
const char* WIFI_PASSWORD = "SUA_SENHA_WIFI";

// MQTT: ID, server IP, port, username and password
const PROGMEM char* MQTT_CLIENT_ID = "cozinha_fita_de_led";
const PROGMEM char* MQTT_SERVER_IP = "IP_DO_SERVIDOR_MQTT";
const PROGMEM uint16_t MQTT_SERVER_PORT = 1883;
const PROGMEM char* MQTT_USER = "USUARIO_MQTT";
const PROGMEM char* MQTT_PASSWORD = "SENHA_MQTT";

// MQTT: topics
// state
const PROGMEM char* MQTT_LIGHT_STATE_TOPIC = "casa/cozinha/fita_de_led/light/status";
const PROGMEM char* MQTT_LIGHT_COMMAND_TOPIC = "casa/cozinha/fita_de_led/light/switch";

// brightness
const PROGMEM char* MQTT_LIGHT_BRIGHTNESS_STATE_TOPIC = "casa/cozinha/fita_de_led/brightness/status";
const PROGMEM char* MQTT_LIGHT_BRIGHTNESS_COMMAND_TOPIC = "casa/cozinha/fita_de_led/brightness/set";

// colors (rgb)
const PROGMEM char* MQTT_LIGHT_RGB_STATE_TOPIC = "casa/cozinha/fita_de_led/rgb/status";
const PROGMEM char* MQTT_LIGHT_RGB_COMMAND_TOPIC = "casa/cozinha/fita_de_led/rgb/set";

// payloads by default (on/off)
const PROGMEM char* LIGHT_ON = "ON";
const PROGMEM char* LIGHT_OFF = "OFF";

// variables used to store the state, the brightness and the color of the light
boolean m_rgb_state = false;
uint8_t m_rgb_brightness = 100;
uint8_t m_rgb_red = 255;
uint8_t m_rgb_green = 255;
uint8_t m_rgb_blue = 255;

// pins used for the rgb led (PWM)
const PROGMEM uint8_t RGB_LIGHT_RED_PIN = 5;
const PROGMEM uint8_t RGB_LIGHT_GREEN_PIN = 0;
const PROGMEM uint8_t RGB_LIGHT_BLUE_PIN = 4;

// buffer used to send/receive data with MQTT
const uint8_t MSG_BUFFER_SIZE = 20;
char m_msg_buffer[MSG_BUFFER_SIZE]; 

WiFiClient wifiClient;
PubSubClient client(wifiClient);

// function called to adapt the brightness and the color of the led
void setColor(uint8_t p_red, uint8_t p_green, uint8_t p_blue) {
  // convert the brightness in % (0-100%) into a digital value (0-255)
  uint8_t brightness = map(m_rgb_brightness, 0, 100, 0, 255);

      if ( brightness == 255 ){
      p_red = 255 - p_red;
      p_green = 255 - p_green;
      p_blue = 255 - p_blue; 
    }else{
    //255 - 100%
    //brightness -  x
    // x = (brightness*100)/255
      p_red = 255 - p_red*brightness/255;
      p_green = 255 - p_green*brightness/255;
      p_blue = 255 - p_blue*brightness/255; 
    }
    
   Serial.print("COR: ");
        Serial.print("VERMELHO: ");
        Serial.print(p_red);
        Serial.print("Verde: ");
        Serial.print(p_green);
        Serial.print("Azul: ");
        Serial.print(p_blue);
        Serial.print("Brilho: ");
        Serial.print(brightness);
    Serial.print(" ");

          
      analogWrite(RGB_LIGHT_RED_PIN, p_red);
      analogWrite(RGB_LIGHT_GREEN_PIN, p_green);
      analogWrite(RGB_LIGHT_BLUE_PIN, p_blue);

//  analogWrite(RGB_LIGHT_RED_PIN, map(p_red, 0, 255, 0, brightness));
//  analogWrite(RGB_LIGHT_GREEN_PIN, map(p_green, 0, 255, 0, brightness));
//  analogWrite(RGB_LIGHT_BLUE_PIN, map(p_blue, 0, 255, 0, brightness));
}

// function called to publish the state of the led (on/off)
void publishRGBState() {
  if (m_rgb_state) {
    client.publish(MQTT_LIGHT_STATE_TOPIC, LIGHT_ON, true);
  } else {
    client.publish(MQTT_LIGHT_STATE_TOPIC, LIGHT_OFF, true);
  }
}

// function called to publish the brightness of the led (0-100)
void publishRGBBrightness() {
  snprintf(m_msg_buffer, MSG_BUFFER_SIZE, "%d", m_rgb_brightness);
  client.publish(MQTT_LIGHT_BRIGHTNESS_STATE_TOPIC, m_msg_buffer, true);
}

// function called to publish the colors of the led (xx(x),xx(x),xx(x))
void publishRGBColor() {
  snprintf(m_msg_buffer, MSG_BUFFER_SIZE, "%d,%d,%d", m_rgb_red, m_rgb_green, m_rgb_blue);
  client.publish(MQTT_LIGHT_RGB_STATE_TOPIC, m_msg_buffer, true);
}

// function called when a MQTT message arrived
void callback(char* p_topic, byte* p_payload, unsigned int p_length) {
  // concat the payload into a string
  String payload;
  for (uint8_t i = 0; i < p_length; i++) {
    payload.concat((char)p_payload[i]);
  }
  // handle message topic
  if (String(MQTT_LIGHT_COMMAND_TOPIC).equals(p_topic)) {
    // test if the payload is equal to "ON" or "OFF"
    if (payload.equals(String(LIGHT_ON))) {
      if (m_rgb_state != true) {
        m_rgb_state = true;
        setColor(m_rgb_red, m_rgb_green, m_rgb_blue);
        publishRGBState();
      }
    } else if (payload.equals(String(LIGHT_OFF))) {
      if (m_rgb_state != false) {
        m_rgb_state = false;
        setColor(0, 0, 0);
        publishRGBState();
      }
    }
  } else if (String(MQTT_LIGHT_BRIGHTNESS_COMMAND_TOPIC).equals(p_topic)) {
    uint8_t brightness = payload.toInt();
    if (brightness < 0 || brightness > 100) {
      // do nothing...
      return;
    } else {
      m_rgb_brightness = brightness;
      setColor(m_rgb_red, m_rgb_green, m_rgb_blue);
      publishRGBBrightness();
    }
  } else if (String(MQTT_LIGHT_RGB_COMMAND_TOPIC).equals(p_topic)) {
    // get the position of the first and second commas
    uint8_t firstIndex = payload.indexOf(',');
    uint8_t lastIndex = payload.lastIndexOf(',');
    
    uint8_t rgb_red = payload.substring(0, firstIndex).toInt();
    if (rgb_red < 0 || rgb_red > 255) {
      return;
    } else {
      m_rgb_red = rgb_red;
    }
    
    uint8_t rgb_green = payload.substring(firstIndex + 1, lastIndex).toInt();
    if (rgb_green < 0 || rgb_green > 255) {
      return;
    } else {
      m_rgb_green = rgb_green;
    }
    
    uint8_t rgb_blue = payload.substring(lastIndex + 1).toInt();
    if (rgb_blue < 0 || rgb_blue > 255) {
      return;
    } else {
      m_rgb_blue = rgb_blue;
    }
    
    setColor(m_rgb_red, m_rgb_green, m_rgb_blue);
    publishRGBColor();
  }
}

void reconnect() {
  // Loop until we're reconnected
  while (!client.connected()) {
    Serial.println("INFO: Attempting MQTT connection...");
    // Attempt to connect
    if (client.connect(MQTT_CLIENT_ID, MQTT_USER, MQTT_PASSWORD)) {
      Serial.println("INFO: connected");
      
      // Once connected, publish an announcement...
      // publish the initial values
      publishRGBState();
      publishRGBBrightness();
      publishRGBColor();

      // ... and resubscribe
      client.subscribe(MQTT_LIGHT_COMMAND_TOPIC);
      client.subscribe(MQTT_LIGHT_BRIGHTNESS_COMMAND_TOPIC);
      client.subscribe(MQTT_LIGHT_RGB_COMMAND_TOPIC);
    } else {
      Serial.print("ERROR: failed, rc=");
      Serial.print(client.state());
      Serial.println("DEBUG: try again in 5 seconds");
      // Wait 5 seconds before retrying
      delay(5000);
    }
  }
}

void setup() {
  // init the serial
  Serial.begin(9600);

  // init the RGB led
  pinMode(RGB_LIGHT_BLUE_PIN, OUTPUT);
  pinMode(RGB_LIGHT_RED_PIN, OUTPUT);
  pinMode(RGB_LIGHT_GREEN_PIN, OUTPUT);
  analogWrite(RGB_LIGHT_BLUE_PIN, 255);
  analogWrite(RGB_LIGHT_RED_PIN, 255);
  analogWrite(RGB_LIGHT_GREEN_PIN, 255);
  analogWriteRange(255);
  setColor(0, 0, 0);

  testRGB();
  // init the WiFi connection
  Serial.println();
  Serial.println();
  Serial.print("INFO: Connecting to ");
  WiFi.mode(WIFI_STA);
  Serial.println(WIFI_SSID);
  WiFi.begin(WIFI_SSID, WIFI_PASSWORD);

  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }

  Serial.println("");
  Serial.println("INFO: WiFi connected");
  Serial.print("INFO: IP address: ");
  Serial.println(WiFi.localIP());

  // init the MQTT connection
  client.setServer(MQTT_SERVER_IP, MQTT_SERVER_PORT);
  client.setCallback(callback);
}

void loop() {
  if (!client.connected()) {
    reconnect();
  }
  client.loop();
}

void testRGB() { // fade in and out of Red, Green, Blue

  analogWrite(RGB_LIGHT_RED_PIN, 255); // R off
  analogWrite(RGB_LIGHT_GREEN_PIN, 255); // G off
  analogWrite(RGB_LIGHT_BLUE_PIN, 255); // B off
  
  fade(RGB_LIGHT_RED_PIN); // R
  fade(RGB_LIGHT_GREEN_PIN); // G
  fade(RGB_LIGHT_BLUE_PIN); // B
  
  analogWrite(RGB_LIGHT_RED_PIN, 255); // R off
  analogWrite(RGB_LIGHT_GREEN_PIN, 255); // G off
  analogWrite(RGB_LIGHT_BLUE_PIN, 255); // B off
}


void fade(int pin) {
  for (int u = 0; u < 255; u++) {
    analogWrite(pin, 255 - u);
    delay(1);
  }
  for (int u = 0; u < 255; u++) {
    analogWrite(pin, u);
    delay(1);
  }
}

*Editar as informações de seu WIFI e servidor MQTT. O exemplo está como fita led para cozinha.

CODIGO PARA SUBIR NO HA:

light:
platform: mqtt
name: ‘Fita de Led RGB’
state_topic: ‘casa/cozinha/fita_de_led/light/status’
command_topic: ‘casa/cozinha/fita_de_led/light/switch’
brightness_state_topic: ‘casa/cozinha/fita_de_led/brightness/status’
brightness_command_topic: ‘casa/cozinha/fita_de_led/brightness/set’
rgb_state_topic: ‘casa/cozinha/fita_de_led/rgb/status’
rgb_command_topic: ‘casa/cozinha/fita_de_led/rgb/set’
brightness_scale: 100
optimistic: false

Aqui nos testes de bancadas funcionou muito bem, brilho e as cores tb, inclusive com comandos do Google Mini.

Se fizar upgrade no código, não deixe de compartilhar :slight_smile:

Espero ter ajudado!
Abraço

6 Curtidas

Ótimo!!! Parabéns pelo projeto, e com certeza irei replicar! :clap:t2::clap:t2:

1 Curtida

Aproveitando: tem algum exemplo desse usando o Tasmota?

1 Curtida

Com tasmota eu nunca vi. Eu ja fiz usando ESPHome

1 Curtida

Comigo não funcionou com o led reg 12v! A cor vermelha não aparece. =/

O vermelho é uma das cores primárias, tenta inverter com outra cor para vc se não está com problema na fita. Uma outra sugestão é deixar o esp conectado no USB e abrir o monitor seria na IDE do Arduino, assim pode conferir em tempo real as cores que está operando, veja no monitor serial como fica quando manda o vermelho.

Exatamente o que eu precisava! Novo no HA, migrei recentemente do HomeBridge e não muito familiarizado com MQTT. Muitíssimo obrigado por disponibilizar aqui.