diff --git a/wled00/FX.h b/wled00/FX.h index 348a495e5..12eb11f6a 100644 --- a/wled00/FX.h +++ b/wled00/FX.h @@ -581,7 +581,7 @@ class WS2812FX { } void - finalizeInit(uint16_t countPixels, bool skipFirst), + finalizeInit(uint16_t countPixels), service(void), blur(uint8_t), fill(uint32_t), @@ -813,7 +813,6 @@ class WS2812FX { void handle_palette(void); bool - _skipFirstMode, _triggered; mode_ptr _mode[MODE_COUNT]; // SRAM footprint: 4 bytes per element diff --git a/wled00/FX_fcn.cpp b/wled00/FX_fcn.cpp index 7d964cb49..8e937d741 100644 --- a/wled00/FX_fcn.cpp +++ b/wled00/FX_fcn.cpp @@ -61,16 +61,11 @@ #endif //do not call this method from system context (network callback) -void WS2812FX::finalizeInit(uint16_t countPixels, bool skipFirst) +void WS2812FX::finalizeInit(uint16_t countPixels) { RESET_RUNTIME; _length = countPixels; - _skipFirstMode = skipFirst; - _lengthRaw = _length; - if (_skipFirstMode) { - _lengthRaw += LED_SKIP_AMOUNT; - } //if busses failed to load, add default (FS issue...) if (busses.getNumBusses() == 0) { @@ -204,7 +199,6 @@ void WS2812FX::setPixelColor(uint16_t i, byte r, byte g, byte b, byte w) } } - uint16_t skip = _skipFirstMode ? LED_SKIP_AMOUNT : 0; if (SEGLEN) {//from segment //color_blend(getpixel, col, _bri_t); (pseudocode for future blending of segments) @@ -216,7 +210,6 @@ void WS2812FX::setPixelColor(uint16_t i, byte r, byte g, byte b, byte w) } uint32_t col = ((w << 24) | (r << 16) | (g << 8) | (b)); - /* Set all the pixels in the group, ensuring _skipFirstMode is honored */ bool reversed = IS_REVERSE; uint16_t realIndex = realPixelIndex(i); @@ -226,22 +219,17 @@ void WS2812FX::setPixelColor(uint16_t i, byte r, byte g, byte b, byte w) if (IS_MIRROR) { //set the corresponding mirrored pixel uint16_t indexMir = SEGMENT.stop - indexSet + SEGMENT.start - 1; if (indexMir < customMappingSize) indexMir = customMappingTable[indexMir]; - busses.setPixelColor(indexMir + skip, col); + busses.setPixelColor(indexMir, col); } if (indexSet < customMappingSize) indexSet = customMappingTable[indexSet]; - busses.setPixelColor(indexSet + skip, col); + busses.setPixelColor(indexSet, col); } } } else { //live data, etc. if (i < customMappingSize) i = customMappingTable[i]; uint32_t col = ((w << 24) | (r << 16) | (g << 8) | (b)); - busses.setPixelColor(i + skip, col); - } - if (skip && i == 0) { - for (uint16_t j = 0; j < skip; j++) { - busses.setPixelColor(j, BLACK); - } + busses.setPixelColor(i, col); } } @@ -514,8 +502,6 @@ uint32_t WS2812FX::getPixelColor(uint16_t i) i = realPixelIndex(i); if (i < customMappingSize) i = customMappingTable[i]; - - if (_skipFirstMode) i += LED_SKIP_AMOUNT; if (i >= _lengthRaw) return 0; diff --git a/wled00/bus_manager.h b/wled00/bus_manager.h index 8dfd4fb39..b461cc539 100644 --- a/wled00/bus_manager.h +++ b/wled00/bus_manager.h @@ -17,9 +17,11 @@ struct BusConfig { uint16_t start = 0; uint8_t colorOrder = COL_ORDER_GRB; bool reversed = false; + uint8_t skipAmount; uint8_t pins[5] = {LEDPIN, 255, 255, 255, 255}; - BusConfig(uint8_t busType, uint8_t* ppins, uint16_t pstart, uint16_t len = 1, uint8_t pcolorOrder = COL_ORDER_GRB, bool rev = false) { - type = busType; count = len; start = pstart; colorOrder = pcolorOrder; reversed = rev; + BusConfig(uint8_t busType, uint8_t* ppins, uint16_t pstart, uint16_t len = 1, uint8_t pcolorOrder = COL_ORDER_GRB, bool rev = false, uint8_t skip=0) { + type = busType; count = len; start = pstart; + colorOrder = pcolorOrder; reversed = rev; skipAmount = skip; uint8_t nPins = 1; if (type > 47) nPins = 2; else if (type > 41 && type < 46) nPins = NUM_PWM_PINS(type); @@ -51,11 +53,11 @@ class Bus { virtual uint8_t getPins(uint8_t* pinArray) { return 0; } - uint16_t getStart() { + inline uint16_t getStart() { return _start; } - void setStart(uint16_t start) { + inline void setStart(uint16_t start) { _start = start; } @@ -69,14 +71,28 @@ class Bus { return COL_ORDER_RGB; } - uint8_t getType() { + virtual bool isRgbw() { + return false; + } + + virtual uint8_t skippedLeds() { + return 0; + } + + inline uint8_t getType() { return _type; } - bool isOk() { + inline bool isOk() { return _valid; } + static bool isRgbw(uint8_t type) { + if (type == TYPE_SK6812_RGBW || type == TYPE_TM1814) return true; + if (type > TYPE_ONOFF && type <= TYPE_ANALOG_5CH && type != TYPE_ANALOG_3CH) return true; + return false; + } + bool reversed = false; protected: @@ -99,8 +115,9 @@ class BusDigital : public Bus { cleanup(); return; } } - _len = bc.count; reversed = bc.reversed; + _skip = bc.skipAmount; //sacrificial pixels + _len = bc.count + _skip; _iType = PolyBus::getI(bc.type, _pins, nr); if (_iType == I_NONE) return; _busPtr = PolyBus::create(_iType, _pins, _len); @@ -109,11 +126,11 @@ class BusDigital : public Bus { //Serial.printf("Successfully inited strip %u (len %u) with type %u and pins %u,%u (itype %u)\n",nr, len, type, pins[0],pins[1],_iType); }; - void show() { + inline void show() { PolyBus::show(_busPtr, _iType); } - bool canShow() { + inline bool canShow() { return PolyBus::canShow(_busPtr, _iType); } @@ -130,20 +147,22 @@ class BusDigital : public Bus { void setPixelColor(uint16_t pix, uint32_t c) { if (reversed) pix = _len - pix -1; + else pix += _skip; PolyBus::setPixelColor(_busPtr, _iType, pix, c, _colorOrder); } uint32_t getPixelColor(uint16_t pix) { if (reversed) pix = _len - pix -1; + else pix += _skip; return PolyBus::getPixelColor(_busPtr, _iType, pix, _colorOrder); } - uint8_t getColorOrder() { + inline uint8_t getColorOrder() { return _colorOrder; } - uint16_t getLength() { - return _len; + inline uint16_t getLength() { + return _len - _skip; } uint8_t getPins(uint8_t* pinArray) { @@ -157,7 +176,15 @@ class BusDigital : public Bus { _colorOrder = colorOrder; } - void reinit() { + inline bool isRgbw() { + return (_type == TYPE_SK6812_RGBW || _type == TYPE_TM1814); + } + + inline uint8_t skippedLeds() { + return _skip; + } + + inline void reinit() { PolyBus::begin(_busPtr, _iType, _pins); } @@ -180,6 +207,7 @@ class BusDigital : public Bus { uint8_t _pins[2] = {255, 255}; uint8_t _iType = I_NONE; uint16_t _len = 0; + uint8_t _skip = 0; void * _busPtr = nullptr; }; @@ -255,7 +283,7 @@ class BusPwm : public Bus { } } - void setBrightness(uint8_t b) { + inline void setBrightness(uint8_t b) { _bri = b; } @@ -265,7 +293,11 @@ class BusPwm : public Bus { return numPins; } - void cleanup() { + bool isRgbw() { + return (_type > TYPE_ONOFF && _type <= TYPE_ANALOG_5CH && _type != TYPE_ANALOG_3CH); + } + + inline void cleanup() { deallocatePins(); } @@ -304,7 +336,7 @@ class BusManager { }; //utility to get the approx. memory usage of a given BusConfig - uint32_t memUsage(BusConfig &bc) { + static uint32_t memUsage(BusConfig &bc) { uint8_t type = bc.type; uint16_t len = bc.count; if (type < 32) { @@ -333,8 +365,7 @@ class BusManager { } else { busses[numBusses] = new BusPwm(bc); } - numBusses++; - return numBusses -1; + return numBusses++; } //do not call this method from system context (network callback) @@ -358,6 +389,7 @@ class BusManager { uint16_t bstart = b->getStart(); if (pix < bstart || pix >= bstart + b->getLength()) continue; busses[i]->setPixelColor(pix - bstart, c); + break; } } @@ -389,14 +421,18 @@ class BusManager { return busses[busNr]; } - uint8_t getNumBusses() { + inline uint8_t getNumBusses() { return numBusses; } - static bool isRgbw(uint8_t type) { - if (type == TYPE_SK6812_RGBW || type == TYPE_TM1814) return true; - if (type > TYPE_ONOFF && type <= TYPE_ANALOG_5CH && type != TYPE_ANALOG_3CH) return true; - return false; + uint16_t getTotalLength() { + uint16_t len = 0; + for (uint8_t i=0; igetLength(); + return len; + } + + static inline bool isRgbw(uint8_t type) { + return Bus::isRgbw(type); } //Return true if the strip requires a refresh to stay off. diff --git a/wled00/bus_wrapper.h b/wled00/bus_wrapper.h index e5e5db54c..e8e6fc654 100644 --- a/wled00/bus_wrapper.h +++ b/wled00/bus_wrapper.h @@ -837,7 +837,7 @@ class PolyBus { } //gives back the internal type index (I_XX_XXX_X above) for the input - static uint8_t getI(uint8_t busType, uint8_t* pins, uint8_t num = 0) { + static uint8_t getI(uint8_t busType, uint8_t* pins, uint8_t num = 0, bool rgbwOverride = false) { if (!IS_DIGITAL(busType)) return I_NONE; if (IS_2PIN(busType)) { //SPI LED chips bool isHSPI = false; @@ -863,7 +863,7 @@ class PolyBus { switch (busType) { case TYPE_WS2812_RGB: case TYPE_WS2812_WWA: - return I_8266_U0_NEO_3 + offset; + return (rgbwOverride ? I_8266_U0_NEO_4 : I_8266_U0_NEO_3) + offset; case TYPE_SK6812_RGBW: return I_8266_U0_NEO_4 + offset; case TYPE_WS2811_400KHZ: @@ -877,7 +877,7 @@ class PolyBus { switch (busType) { case TYPE_WS2812_RGB: case TYPE_WS2812_WWA: - return I_32_R0_NEO_3 + offset; + return (rgbwOverride ? I_32_R0_NEO_3 : I_32_R0_NEO_4) + offset; case TYPE_SK6812_RGBW: return I_32_R0_NEO_4 + offset; case TYPE_WS2811_400KHZ: diff --git a/wled00/cfg.cpp b/wled00/cfg.cpp index 827e98a00..1b94c00ff 100644 --- a/wled00/cfg.cpp +++ b/wled00/cfg.cpp @@ -103,7 +103,7 @@ bool deserializeConfig(JsonObject doc, bool fromFS) { if (length==0) continue; uint8_t colorOrder = (int)elm[F("order")]; //only use skip from the first strip (this shouldn't have been in ins obj. but remains here for compatibility) - if (s==0) skipFirstLed = elm[F("skip")]; + uint8_t skipFirst = elm[F("skip")]; uint16_t start = elm[F("start")] | 0; if (start >= ledCount) continue; //limit length of strip if it would exceed total configured LEDs @@ -115,11 +115,11 @@ bool deserializeConfig(JsonObject doc, bool fromFS) { //refresh is required to remain off if at least one of the strips requires the refresh. strip.isOffRefreshRequred |= BusManager::isOffRefreshRequred(ledType); s++; - BusConfig bc = BusConfig(ledType, pins, start, length, colorOrder, reversed); + BusConfig bc = BusConfig(ledType, pins, start, length, colorOrder, reversed, skipFirst); mem += busses.memUsage(bc); if (mem <= MAX_LED_MEMORY) busses.add(bc); } - strip.finalizeInit(ledCount, skipFirstLed); + strip.finalizeInit(ledCount); } if (hw_led["rev"]) busses.getBus(0)->reversed = true; //set 0.11 global reversed setting for first bus @@ -488,7 +488,7 @@ void serializeConfig() { for (uint8_t i = 0; i < nPins; i++) ins_pin.add(pins[i]); ins[F("order")] = bus->getColorOrder(); ins["rev"] = bus->reversed; - ins[F("skip")] = (skipFirstLed && s == 0) ? 1 : 0; + ins[F("skip")] = bus->skippedLeds(); ins["type"] = bus->getType(); } diff --git a/wled00/data/settings_leds.htm b/wled00/data/settings_leds.htm index fd8308222..2addd7325 100644 --- a/wled00/data/settings_leds.htm +++ b/wled00/data/settings_leds.htm @@ -235,7 +235,9 @@
Start:  
- Count:
+ Count:
+ Skip 1st LED:   + Reverse:
`; f.insertAdjacentHTML("beforeend", cn); @@ -338,7 +340,6 @@
- Skip first LED:
Auto-calculate white channel from RGB: