Skip to content
  • MySensors
  • OpenHardware.io
  • Categories
  • Recent
  • Tags
  • Popular
Skins
  • Light
  • Brite
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Brand Logo
  1. Home
  2. Development
  3. RGB Leds Light - Mood Light

RGB Leds Light - Mood Light

Scheduled Pinned Locked Moved Development
6 Posts 2 Posters 2.2k Views 2 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • OliverDogO Offline
    OliverDogO Offline
    OliverDog
    wrote on last edited by
    #1

    I think most people have already seen that 15 dollars multisensor build by Ben from BruhAutomation.
    Here is the link: https://www.youtube.com/watch?v=jpjfVc-9IrQ

    Unfortunately (at least for this community) he uses a NomeMCU board instead of using a MySensors connection.

    It would be awesome porting that whole sketch and project to a MySensors battery powered node... sorry if I am missing somebody´s work that already did that.

    All the sensors together are relatively easy to build on mysensor, but what I can´t figure out is that awesome RGB LED wich turns into a complete Light Component, with fade, color changing and transitions.

    Could someone share a mysensors node or help porting that Bruh Sketch, specially the RGB Led part?

    It would be something like a Mood Light!

    Here is original code:
    https://github.com/bruhautomation/ESP-MQTT-JSON-Multisensor

    BartEB 1 Reply Last reply
    0
    • OliverDogO OliverDog

      I think most people have already seen that 15 dollars multisensor build by Ben from BruhAutomation.
      Here is the link: https://www.youtube.com/watch?v=jpjfVc-9IrQ

      Unfortunately (at least for this community) he uses a NomeMCU board instead of using a MySensors connection.

      It would be awesome porting that whole sketch and project to a MySensors battery powered node... sorry if I am missing somebody´s work that already did that.

      All the sensors together are relatively easy to build on mysensor, but what I can´t figure out is that awesome RGB LED wich turns into a complete Light Component, with fade, color changing and transitions.

      Could someone share a mysensors node or help porting that Bruh Sketch, specially the RGB Led part?

      It would be something like a Mood Light!

      Here is original code:
      https://github.com/bruhautomation/ESP-MQTT-JSON-Multisensor

      BartEB Offline
      BartEB Offline
      BartE
      Contest Winner
      wrote on last edited by
      #2

      @OliverDog here is a link to such a sketch (https://forum.mysensors.org/topic/2160/my-mysensors-rgbw-plug-in-has-an-init-problem)

      1 Reply Last reply
      1
      • OliverDogO Offline
        OliverDogO Offline
        OliverDog
        wrote on last edited by
        #3

        Thanks @BartE !

        Three more questions:

        • Will it work with a single 4 pin RGB LED common cathode instead of a LED strip?
        • Will it work with Home Assistant Controller like a ordinary RGB Light?
        • Could it run on batteries?

        Thanks again.

        1 Reply Last reply
        0
        • BartEB Offline
          BartEB Offline
          BartE
          Contest Winner
          wrote on last edited by
          #4

          Hi @OliverDog , yes this should work

          • Will it work with a single 4 pin RGB LED common cathode instead of a LED strip?
            --> Uncomment this line "#define RGBW 1" to make it three color (RGB) in stead of four (RGBW).

          • Will it work with Home Assistant Controller like a ordinary RGB Light?
            --> Should work with HAC since it presents it self as a RGB module

          • Could it run on batteries?
            --> Yes why not, but please do read some forum posts about what to think about when running mysensors on batteries, there are several of them

          1 Reply Last reply
          1
          • OliverDogO Offline
            OliverDogO Offline
            OliverDog
            wrote on last edited by OliverDog
            #5

            Finally I tried this weekend but no success...

            First I have updated your sketch to 2.0 version (I think I made everything right)
            Didn't work on Home Assistant because the sketch don't send an initial value for each configuration of the Leds, such as Dimmer, RGB, Light, Fade, etc.

            I did not figure out how to create an initial value loop because there are no MyMessage msg(Child_, V_) on the sketch...

            Could you help me again?
            Thanks very much...

            Here is the updated sketch:

            // RBG led strip plug in.
            // by Bart Eversdijk (c) 2015.
            
            #define MY_DEBUG
            #define MY_RADIO_NRF24
            #define MY_NODE_ID 3
            
            #include <MySensors.h>
            #include <SPI.h>
            
            #define SUBID  1  // sensor number needed in the custom devices set up
            
            #define RED   6  // Arduino PWM pin for Red
            #define GREEN 5 // Arduino PWM pin for Green
            #define BLUE  3  // Arduino PWM pin for Blue
            #define NODENAME "RGB Led2"
            
            enum ANIMATIOMODES {RAINBOW=0,RANDONMIZE,FADERGB,FADEMULTICOLR,FLASHCOLOR,LAST_PROGRAM};
            
            byte FADE_RGB_COLOR_MODES[]   = {0b0010,0b0011,0b0100,0b0101,0b1000,0b1001, 0xFF};
            byte FADE_MULTI_COLOR_MODES[] = {0b0010,0b0011,0b0110,0b0111,0b0100,0b0101,0b1100,0b1101,0b1000,0b1001,0b1010,0b1011,0xFF};
            
            static bool first_message_sent = false;
            
            byte rgb_pins[]   = {RED, GREEN, BLUE};
            byte ledOffValues[] = {0, 0, 0, 0};
            byte rgb_values[]   = {0, 0, 0, 0};
            
            
            void incomingMessage(const MyMessage &message);
            #define NUM_OF_COLORS sizeof(rgb_pins)
            int speedtable[] = { 0, 100, 50, 2 };
            #define NUM_OF_SPEEDS sizeof(speedtable)
            
            struct
            {
               byte values[4];
               byte speedsetting;
               byte mode;
               bool status;
            } rgb = { {0,0,0,0}, 0, RAINBOW, false};
            
            bool    flashOn      = true;
            int     syscounter   = 0;
            int     lastUpdate   = 0;
            bool    newSetting   = false;
            
            void before() {
                // Set the rgb(w) pins in output mode
                for (int i = 0; i < NUM_OF_COLORS; i++) {
                    pinMode(rgb_pins[i], OUTPUT);
                }
                recallEeprom();
                setLedValues(rgb.values, true);
                
                Serial.println("Init done");
            }
            
            void presentation()
            {
              sendSketchInfo(NODENAME, "1.0");
              present(SUBID, S_RGB_LIGHT);
            }
            
            void loop()
            {
                // Alway process incoming messages whenever possible
                if (speedtable[rgb.speedsetting] > 0) {
                    if ((syscounter % speedtable[rgb.speedsetting]) == 0) {
                       switch (rgb.mode)
                       {
                           case RAINBOW:
                             animateRainbowStep();
                             break;
            
                           case FADERGB:
                             animateFadeColorStep(FADE_RGB_COLOR_MODES);
                             break;
            
                           case FADEMULTICOLR:
                             animateFadeColorStep(FADE_MULTI_COLOR_MODES);
                             break;
                         
                          case FLASHCOLOR:
                             setLedValues(flashOn ? ledOffValues : rgb.values, false);
                             flashOn = !flashOn;
                             break;
                                         
                           case RANDONMIZE:
                             long number = random(0, 0xFFFFFF);
                             rgb_values[0] = number >> 16 & 0xFF ;
                             rgb_values[1] = number >> 8 & 0xFF ;
                             rgb_values[2] = number & 0xFF;
                             setLedValues(rgb_values, false);
                             break;
                       }
                    }
                    delay(rgb.mode == RANDONMIZE || rgb.mode == FLASHCOLOR ? 50 : 1);
                }
                if (newSetting && (lastUpdate + 30000 < syscounter)) {   
                    // Wait for a couple of seconds be fore actual storing the current setting in to EEPROM
                    // This will save the EEPROM's life time, when playing around with colors
                    Serial.println(" Store EERPOM");
                    storeEeprom();
                    newSetting = false;
                } 
                delay(1);
                syscounter++;
            }
            
            void animateRainbowStep()
            {    
                static float counter = 0;
                float        pi      = 3.14159; 
                counter++;
                rgb_values[0] = map(sin(counter/100         )*1000,-1000,1000,0,255);
                rgb_values[1] = map(sin(counter/100 + pi*2/3)*1000,-1000,1000,0,255);
                rgb_values[2] = map(sin(counter/100 + pi*4/3)*1000,-1000,1000,0,255);
                setLedValues(rgb_values, false);
            }
            
            void animateFadeColorStep(byte *modes)
            {    
                static int modecnt = 0;
                if (updateRGBValues(modes[modecnt] >> 1, (modes[modecnt] & 0x1) == 0x1)) { 
                    modecnt = (modes[modecnt+1] == 0xFF ? 0 : modecnt + 1);
                }
            }
            
            bool updateRGBValues(byte mode, bool down)
            {
                bool endReached = false;
                for (byte i = 0; i < 3; i++) {
                    if (((mode >> i) & 0x1) == 0x1) {
                       rgb_values[i] += (down ? -1 : 1);
                       endReached    |= (down && (rgb_values[i] == 0x00)) || (!down && (rgb_values[i] == 0xFF));
                    }
                }
                setLedValues(rgb_values, false);
                return endReached;
            }
            
            
            void incomingMessage(const MyMessage &message) {
                if (message.type == V_RGB || message.type == V_RGBW) {
              // starting to process the hex code
                    String hexstring = message.getString();
            
                    long number;
            #ifdef RGBW
                    char white[3];
                    white[0] = hexstring[6];
                    white[1] = hexstring[7];
                    white[2] = 0;
                    number = (long) strtol( &white[0], NULL, 16);
                    rgb.values[3] = number & 0xFF;
            #endif        
                    hexstring[6] = 0;
                    number = (long) strtol( &hexstring[0], NULL, 16);
                    rgb.values[0] = number >> 16 & 0xFF ;
                    rgb.values[1] = number >> 8 & 0xFF ;
                    rgb.values[2] = number & 0xFF;
                    
                    rgb.speedsetting = 0;
                    setLedValues(rgb.values, true);
                    lastUpdate = syscounter;
                    newSetting = true;
                }
                
                if (message.type == V_STATUS) {
                  if (message.getBool()) {
                      Serial.println("ON: Switch to last known color values");
                      setLedValues(rgb_values, true);
                  } else {
                     Serial.println("OFF: Switch colors off");
                     setLedValues(ledOffValues, true);
                  }
                  rgb.speedsetting = 0;
                  rgb.status = message.getBool();
                  lastUpdate = syscounter;
                  newSetting = true;
                }
                
                if (message.type == V_VAR1) {
                   Serial.println("Set speed and program value"); 
                   byte newsetting = message.getByte();
                   rgb.speedsetting = (newsetting >> 4) & 0x0F;
                   byte newmode = newsetting & 0x0F;
            
                   if (newmode != rgb.mode) {
                       for (byte i = 0; i < NUM_OF_COLORS; i++) {
                           rgb_values[i] = 0;
                       }
                       rgb.mode = newmode;
                   }
                   if (rgb.speedsetting > 0) {
                     rgb.status = true;
                   }
                   lastUpdate = syscounter;
                   newSetting = true;
                  
                   Serial.print("Data 0x");
                   Serial.print(newsetting, HEX);
                   Serial.print(" speed:");
                   Serial.print(rgb.speedsetting);
                   Serial.print(" mode:");
                   Serial.println(rgb.mode);
                }
            }
            
            void setLedValues(byte *rgb, bool show)
            {
                for (int i = 0; i < NUM_OF_COLORS; i++) {
                    analogWrite(rgb_pins[i], rgb[i]);
                }  
             
                if (show) {
                  Serial.print("Red: " );
                  Serial.print(rgb[0], HEX);
                  Serial.print("  Green: " );
                  Serial.print(rgb[1], HEX);
                  Serial.print("  Blue: " );
                  Serial.print(rgb[2], HEX);
             #ifdef RGBW
                    Serial.print("  White is " );
                    Serial.print(rgb[3], HEX);
             #endif
                  Serial.println();
                }
            }
            
            void storeEeprom()
            {
                byte address = 0;
                byte *p = (byte *)&(rgb);
                for (byte i = 0; i < sizeof(rgb); i++) {
                   saveState(address++, p[i]);
                }
            }
            
            void recallEeprom()
            {
                byte address = 0;
                byte *p = (byte *)&(rgb);
                for (byte i = 0; i < sizeof(rgb); i++) {
                   p[i] = loadState(address++);
                }
            }
            
            1 Reply Last reply
            0
            • OliverDogO Offline
              OliverDogO Offline
              OliverDog
              wrote on last edited by
              #6

              I tried another sketch from
              https://forum.mysensors.org/topic/6765/rgb-led-strip

              It worked with HASS but there is no response based on transitions time.

              /**
               * This program is free software; you can redistribute it and/or
               * modify it under the terms of the GNU General Public License
               * version 2 as published by the Free Software Foundation.
               *
               * LED STRIP sketch for Mysensors
               *******************************
               *
               * REVISION HISTORY
               * 1.0 
               *   Based on the example sketch in mysensors
               * 1.1
               *   fadespeed parameter (send as V_VAR1 message)
               *   HomeAssistant compatible (send status to ack)
               */
              
              #define MY_NODE_ID AUTO
              #define MY_DEBUG
              #define MY_RADIO_NRF24
              
              #include <MySensors.h>
              
              #define CHILD_ID_LIGHT 1
              
              #define SN "LED Strip"
              #define SV "1.1"
              
              MyMessage lightMsg(CHILD_ID_LIGHT, V_LIGHT);
              MyMessage rgbMsg(CHILD_ID_LIGHT, V_RGB);
              MyMessage dimmerMsg(CHILD_ID_LIGHT, V_DIMMER);
              
              byte red = 255;
              byte green = 255;
              byte blue = 255;
              byte r0 = 255;
              byte g0 = 255;
              byte b0 = 255;
              char rgbstring[] = "ffffff";
              
              int on_off_status = 0;
              int dimmerlevel = 100;
              int fadespeed = 0;
              
              #define REDPIN 6
              #define GREENPIN 5
              #define BLUEPIN 3
              
              void setup()
              {
                // Fix the PWM timer. Without this the LEDs will flicker.
                TCCR0A = _BV(COM0A1) | _BV(COM0B1) | _BV(WGM00);
              
                // Output pins
                pinMode(REDPIN, OUTPUT);
                pinMode(GREENPIN, OUTPUT);
                pinMode(BLUEPIN, OUTPUT);
                
              }
              
              void presentation()
              {
              	// Send the Sketch Version Information to the Gateway
              	sendSketchInfo(SN, SV);
              	present(CHILD_ID_LIGHT, S_RGB_LIGHT);
              }
              
              void loop()
              {
                static bool first_message_sent = false;
                if ( first_message_sent == false ) {
                  Serial.println( "Sending initial state..." );
                  set_hw_status();
                  send_status();
                  first_message_sent = true;
                }
              }
              
              void receive(const MyMessage &message)
              {
                int val;
                
              	if (message.type == V_RGB) {
              		Serial.println( "V_RGB command: " );
                  Serial.println(message.data);
                  long number = (long) strtol( message.data, NULL, 16);
              
                  // Save old value
                  strcpy(rgbstring, message.data);
                  
                  // Split it up into r, g, b values
                  red = number >> 16;
                  green = number >> 8 & 0xFF;
                  blue = number & 0xFF;
              
                  send_status();
                  set_hw_status();
              
              	} else if (message.type == V_LIGHT || message.type == V_STATUS) {
                  Serial.println( "V_LIGHT command: " );
                  Serial.println(message.data);
                  val = atoi(message.data);
                  if (val == 0 or val == 1) {
                    on_off_status = val;
                    send_status();
                    set_hw_status();
                  }
                  
                } else if (message.type == V_DIMMER || message.type == V_PERCENTAGE) {
                  Serial.print( "V_DIMMER command: " );
                  Serial.println(message.data);
                  val = atoi(message.data);
                  if (val >= 0 and val <=100) {
                    dimmerlevel = val;
                    send_status();
                    set_hw_status();
                  }
                  
                } else if (message.type == V_VAR1 ) {
                  Serial.print( "V_VAR1 command: " );
                  Serial.println(message.data);
                  val = atoi(message.data);
                  if (val >= 0 and val <= 2000) {
                    fadespeed = val;
                  }
                  
              	} else {
              		Serial.println( "Invalid command received..." );
              		return;
              	}
              
              }
              
              void set_rgb(int r, int g, int b) {
                analogWrite(REDPIN, r);
                analogWrite(GREENPIN, g);
                analogWrite(BLUEPIN, b);
              }
              
              void set_hw_status() {
                int r = on_off_status * (int)(red * dimmerlevel/100.0);
                int g = on_off_status * (int)(green * dimmerlevel/100.0);
                int b = on_off_status * (int)(blue * dimmerlevel/100.0);
              
                if (fadespeed >0) {
                  
                  float dr = (r - r0) / float(fadespeed);
                  float db = (b - b0) / float(fadespeed);
                  float dg = (g - g0) / float(fadespeed);
                  
                  for (int x = 0;  x < fadespeed; x++) {
                    set_rgb(r0 + dr*x, g0 + dg*x, b0 + db*x);
                    delay(100);
                  }
                }
              
                set_rgb(r, g, b);
               
                r0 = r;
                b0 = b;
                g0 = g;
                
              }
              
              
              void send_status() {
                send(rgbMsg.set(rgbstring));
                send(lightMsg.set(on_off_status));
                send(dimmerMsg.set(dimmerlevel));
              }
              
              1 Reply Last reply
              0
              Reply
              • Reply as topic
              Log in to reply
              • Oldest to Newest
              • Newest to Oldest
              • Most Votes


              9

              Online

              11.7k

              Users

              11.2k

              Topics

              113.1k

              Posts


              Copyright 2025 TBD   |   Forum Guidelines   |   Privacy Policy   |   Terms of Service
              • Login

              • Don't have an account? Register

              • Login or register to search.
              • First post
                Last post
              0
              • MySensors
              • OpenHardware.io
              • Categories
              • Recent
              • Tags
              • Popular