diff --git a/70_module_moon.ino b/70_module_moon.ino index 7291367..b81b8ce 100644 --- a/70_module_moon.ino +++ b/70_module_moon.ino @@ -1,183 +1,68 @@ #ifdef ENABLE_MOON -// Needs refactoring -// Use https://adrianotiger.github.io/Neopixel-Effect-Generator/ for inspiration -// Read up on final comment at https://forum.arduino.cc/index.php?topic=534060.0 +#include -#include - -/* - * Based on https://adrianotiger.github.io/Neopixel-Effect-Generator/ - * TODO: Refactor for just a single string effect, less frills - * Rainbow pattern - */ -class Strip -{ -public: - uint8_t effect; - uint8_t effects; - uint16_t effStep; - unsigned long effStart; - Adafruit_NeoPixel strip; - Strip(uint16_t leds, uint8_t pin, uint8_t toteffects) : strip(leds, pin, NEO_GRB + NEO_KHZ800) { - effect = -1; - effects = toteffects; - Reset(); - } - void Reset(){ - effStep = 0; - effect = (effect + 1) % effects; - effStart = millis(); - } -}; - -struct Loop -{ - uint8_t currentChild; - uint8_t childs; - bool timeBased; - uint16_t cycles; - uint16_t currentTime; - Loop(uint8_t totchilds, bool timebased, uint16_t tottime) {currentTime=0;currentChild=0;childs=totchilds;timeBased=timebased;cycles=tottime;} -}; - -Strip strip_0(7, MOON_PIXEL, 7 ); -struct Loop strip0loop0(1, false, 1); - -//[GLOBAL_VARIABLES] -int speed = 200; // started at 101 - -uint8_t strip0_loop0_eff0() { - // Strip ID: 0 - Effect: Rainbow - LEDS: 7 - // Steps: 35 - Delay: 100 - // Colors: 6 (255.255.0, 0.255.0, 0.0.255, 255.0.255, 255.0.0, 255.255.255, ) - // Options: toLeft=true, - if(millis() - strip_0.effStart < 100 * (strip_0.effStep)) return 0x00; - float factor1, factor2; - uint16_t ind; - for(uint16_t j=0;j<7;j++) { - ind = strip_0.effStep + j * 1; - switch((int)((ind % 35) / 5.833333333333333)) { - case 0: factor1 = 1.0 - ((float)(ind % 35 - 0 * 5.833333333333333) / 5.833333333333333); - factor2 = (float)((int)(ind - 0) % 35) / 5.833333333333333; - strip_0.strip.setPixelColor(j, 255 * factor1 + 0 * factor2, 255 * factor1 + 255 * factor2, 0 * factor1 + 0 * factor2); - break; - case 1: factor1 = 1.0 - ((float)(ind % 35 - 1 * 5.833333333333333) / 5.833333333333333); - factor2 = (float)((int)(ind - 5.833333333333333) % 35) / 5.833333333333333; - strip_0.strip.setPixelColor(j, 0 * factor1 + 0 * factor2, 255 * factor1 + 0 * factor2, 0 * factor1 + 255 * factor2); - break; - case 2: factor1 = 1.0 - ((float)(ind % 35 - 2 * 5.833333333333333) / 5.833333333333333); - factor2 = (float)((int)(ind - 11.666666666666666) % 35) / 5.833333333333333; - strip_0.strip.setPixelColor(j, 0 * factor1 + 255 * factor2, 0 * factor1 + 0 * factor2, 255 * factor1 + 255 * factor2); - break; - case 3: factor1 = 1.0 - ((float)(ind % 35 - 3 * 5.833333333333333) / 5.833333333333333); - factor2 = (float)((int)(ind - 17.5) % 35) / 5.833333333333333; - strip_0.strip.setPixelColor(j, 255 * factor1 + 255 * factor2, 0 * factor1 + 0 * factor2, 255 * factor1 + 0 * factor2); - break; - case 4: factor1 = 1.0 - ((float)(ind % 35 - 4 * 5.833333333333333) / 5.833333333333333); - factor2 = (float)((int)(ind - 23.333333333333332) % 35) / 5.833333333333333; - strip_0.strip.setPixelColor(j, 255 * factor1 + 255 * factor2, 0 * factor1 + 255 * factor2, 0 * factor1 + 255 * factor2); - break; - case 5: factor1 = 1.0 - ((float)(ind % 35 - 5 * 5.833333333333333) / 5.833333333333333); - factor2 = (float)((int)(ind - 29.166666666666664) % 35) / 5.833333333333333; - strip_0.strip.setPixelColor(j, 255 * factor1 + 255 * factor2, 255 * factor1 + 255 * factor2, 255 * factor1 + 0 * factor2); - break; - } - } - if(strip_0.effStep >= 35) {strip_0.Reset(); return 0x03; } - else strip_0.effStep++; - return 0x01; -} - -uint8_t strip0_loop0() { - uint8_t ret = 0x00; - switch(strip0loop0.currentChild) { - case 0: - ret = strip0_loop0_eff0();break; - } - if(ret & 0x02) { - ret &= 0xfd; - if(strip0loop0.currentChild + 1 >= strip0loop0.childs) { - strip0loop0.currentChild = 0; - if(++strip0loop0.currentTime >= strip0loop0.cycles) {strip0loop0.currentTime = 0; ret |= 0x02;} - } - else { - strip0loop0.currentChild++; - } - }; - return ret; -} - -void strips_loop() { - if(strip0_loop0() & 0x01) - strip_0.strip.show(); -} +// https://github.com/kitesurfer1404/WS2812FX/blob/master/src/WS2812FX.h +WS2812FX ws2812fx = WS2812FX(MOON_PIXEL_LEDS, MOON_PIXEL, NEO_GRB + NEO_KHZ800); +long color = 0x00A4B3; // Starting color /* * Interface with other modules */ - -void newcmd(String cmd) { - cmd.toLowerCase(); - if(cmd.equals("off")) { - settings.mode = 0; - PRINTLN_SERIAL("Moon off"); - strip_0.strip.setBrightness(0); // 0-255 - state.text = "Moon switched off"; - } - if(cmd.equals("on")) { - settings.mode = 1; - PRINTLN_SERIAL("Moon switched on"); - strip_0.strip.setBrightness(10); // 0-255 - state.text = "Moon switched off"; - } -} -void module_message(const String& shorttopic, const String& message) { +void module_message(const String& shorttopic, const String& message) { //@@@@FIXME@@@@ instead of brightness, adjust mode? char msgptr[10]; String buffer; if(shorttopic.equalsIgnoreCase("cmd")) { - if(message.equalsIgnoreCase("off")) { - state.mode = 0; - PRINTLN_SERIAL("Moon off"); - strip_0.strip.setBrightness(0); // 0-255 - state.text = "Moon switched off"; - } else if(message.equalsIgnoreCase("on")) { - state.mode = 1; - PRINTLN_SERIAL("Moon switched on"); - strip_0.strip.setBrightness(10); // 0-255 - state.text = "Moon switched off"; - } - - } else if(shorttopic.equalsIgnoreCase("mode")) { if(message.equals("off")) { - state.mode = 0; + ws2812fx.setColor(0x000000); + ws2812fx.setMode(FX_MODE_STATIC); PRINTLN_SERIAL("Shutting off"); + } else if(message.equals("on")) { // restore last (static) color state + ws2812fx.setColor(color); + ws2812fx.setMode(FX_MODE_STATIC); + PRINTLN_SERIAL("Swtiching on (static)"); + } else if(message.startsWith("0x")) { - state.mode = 1; message.toCharArray(msgptr, 9); - state.color = strtoll( &msgptr[2], NULL, 16); - sprintf(printbuffer, "Switching to static color 0x%x", state.color); + color = strtoll( &msgptr[2], NULL, 16); + ws2812fx.setColor(color); + ws2812fx.setMode(FX_MODE_STATIC); + sprintf(printbuffer, "Switching to static color 0x%x", color); PRINTLN_SERIAL(printbuffer); } else if(message.startsWith("#")) { - state.mode = 1; message.toCharArray(msgptr, 8); - state.color = strtoll( &msgptr[1], NULL, 16); - sprintf(printbuffer, "Switching to static color 0x%x", state.color); + color = strtoll( &msgptr[1], NULL, 16); + ws2812fx.setColor(color); + ws2812fx.setMode(FX_MODE_STATIC); + sprintf(printbuffer, "Switching to static color 0x%x", color); PRINTLN_SERIAL(printbuffer); + + } else if(message.equals("moon")) { + ws2812fx.setSpeed(20000); + ws2812fx.setLength(20); // Emulate a 20 pin cycle for a 7 pixel moon lamp + ws2812fx.setMode(FX_MODE_RAINBOW_CYCLE); + PRINTLN_SERIAL("Switching to moon mode"); + } else if(message.equals("rainbow")) { - state.mode = 2; + ws2812fx.setSpeed(2000); + ws2812fx.setLength(MOON_PIXEL_LEDS); + ws2812fx.setMode(FX_MODE_RAINBOW_CYCLE); PRINTLN_SERIAL("Switching to rainbow mode"); + +// Testing area for new scenes + } else if(message.equals("twinkle")) { + ws2812fx.setMode(FX_MODE_LARSON_SCANNER); + PRINTLN_SERIAL("Switching to twinkle mode"); + } - mqtt_publish((deviceprefix + "log"), ("mode=" + String(state.mode))); // @@@FIXME@@@ this needs to go elsewhere } else if(shorttopic.equalsIgnoreCase("brightness")) { PRINTLN_SERIAL("Setting brightness to " + message); - settings.brightness = message.toInt(); - strip_0.strip.setBrightness(settings.brightness); + ws2812fx.setBrightness(message.toInt()); // 0-255 buffer = "brightness="; - buffer.concat(settings.brightness); + buffer.concat(message.toInt()); mqtt_publish((deviceprefix + "log"), buffer.c_str()); // @@@FIXME@@@ this needs to go elsewhere } } @@ -188,34 +73,16 @@ void module_message(const String& shorttopic, const String& message) { void moon_setup() { PRINTLN_SERIAL("initialising module Moon"); - strip_0.strip.setBrightness(2); // 0-255 - strip_0.strip.begin(); + ws2812fx.init(); + ws2812fx.setBrightness(5); + ws2812fx.setSpeed(200); + ws2812fx.setColor(0x000000); + ws2812fx.setMode(FX_MODE_STATIC); + ws2812fx.start(); } void moon_loop() { - uint16_t r; - - switch(state.mode) { - case 0: // Off - for(r=0; r< strip_0.strip.numPixels(); r++) { - strip_0.strip.setPixelColor(r, 0,0,0); - } - strip_0.strip.show(); - break; - case 1: // Static color - for(r=0; r< strip_0.strip.numPixels(); r++) { - // Split the set color code up into r, g, b values - int rval = state.color >> 16; - int gval = state.color >> 8 & 0xFF; - int bval = state.color & 0xFF; - strip_0.strip.setPixelColor(r, rval, gval, bval); - } - strip_0.strip.show(); - break; - case 2: // Rainbow - strips_loop(); - break; - } + ws2812fx.service(); } #endif