From d95ba43fd1196ba0a6dbe82b44efcb108e16992d Mon Sep 17 00:00:00 2001 From: Blaz Kristan Date: Mon, 20 Sep 2021 22:24:58 +0200 Subject: [PATCH] Virtual bus implementation. Base for virtual WLED set-up (multiple instances acting as one). UDP broadcast not yet implemented. --- wled00/bus_manager.h | 88 ++- wled00/const.h | 2 + wled00/data/settings_leds.htm | 937 ++++++++++++++--------------- wled00/fcn_declare.h | 1 + wled00/html_settings.h | 55 +- wled00/set.cpp | 50 +- wled00/udp.cpp | 1040 +++++++++++++++++---------------- 7 files changed, 1146 insertions(+), 1027 deletions(-) diff --git a/wled00/bus_manager.h b/wled00/bus_manager.h index f607a001..0bec1e3f 100644 --- a/wled00/bus_manager.h +++ b/wled00/bus_manager.h @@ -353,6 +353,86 @@ class BusPwm : public Bus { } }; + +class BusVirtual : public Bus { + public: + BusVirtual(BusConfig &bc) : Bus(bc.type, bc.start) { + _valid = false; + _data = (byte *)malloc(bc.count * (_rgbw ? 4 : 3)); + if (_data == nullptr) return; + memset(_data, 0, bc.count * (_rgbw ? 4 : 3)); + _len = bc.count; + //_rgbw = bc.rgbwOverride; // RGBW override in bit 7 or can have a special type + _rgbw = _type == TYPE_VIRTUAL_RGBW; + _colorOrder = bc.colorOrder; + _client = IPAddress(bc.pins[0],bc.pins[1],bc.pins[2],bc.pins[3]); + _broadcastLock = false; + _valid = true; + }; + + void setPixelColor(uint16_t pix, uint32_t c) { + if (!_valid || pix >= _len) return; + _data[pix] = 0xFF & (c >> 16); + _data[pix+1] = 0xFF & (c >> 8); + _data[pix+2] = 0xFF & (c ); + if (_rgbw) _data[pix+3] = 0xFF & (c >> 24); + } + + uint32_t getPixelColor(uint16_t pix) { + if (!_valid || pix >= _len) return 0; + return ((_rgbw?(_data[pix+3] << 24):0) | (_data[pix] << 16) | (_data[pix+1] << 8) | (_data[pix+2])); + } + + void show() { + if (!_valid || _broadcastLock) return; + _broadcastLock = true; + realtimeBoroadcast(_client, _len, _data, _rgbw); + _broadcastLock = false; + } + + inline bool canShow() { + return !_broadcastLock; + } + + inline void setBrightness(uint8_t b) { + // not sure if this is correctly implemented + for (uint16_t pix=0; pix<_len; pix++) { + _data[pix ] = scale8(_data[pix ], b); + _data[pix+1] = scale8(_data[pix+1], b); + _data[pix+2] = scale8(_data[pix+2], b); + if (_rgbw) _data[pix+3] = scale8(_data[pix+3], b); + } + } + + inline bool isRgbw() { + return _rgbw; + } + + inline uint16_t getLength() { + return _len; + } + + void cleanup() { + _type = I_NONE; + _valid = false; + if (_data != nullptr) free(_data); + _data = nullptr; + } + + ~BusVirtual() { + cleanup(); + } + + private: + IPAddress _client; + uint16_t _len = 0; + uint8_t _colorOrder; + bool _rgbw; + bool _broadcastLock; + byte* _data; +}; + + class BusManager { public: BusManager() { @@ -363,7 +443,9 @@ class BusManager { static uint32_t memUsage(BusConfig &bc) { uint8_t type = bc.type; uint16_t len = bc.count; - if (type < 32) { + if (type < 4) { + return len * (type+1); + } else if (type < 32) { #ifdef ESP8266 if (bc.pins[0] == 3) { //8266 DMA uses 5x the mem if (type > 29) return len*20; //RGBW @@ -384,7 +466,9 @@ class BusManager { int add(BusConfig &bc) { if (numBusses >= WLED_MAX_BUSSES) return -1; - if (IS_DIGITAL(bc.type)) { + if (bc.type>1 && bc.type<4) { + busses[numBusses] = new BusVirtual(bc); + } else if (IS_DIGITAL(bc.type)) { busses[numBusses] = new BusDigital(bc, numBusses); } else { busses[numBusses] = new BusPwm(bc); diff --git a/wled00/const.h b/wled00/const.h index db63b7c4..27eff968 100644 --- a/wled00/const.h +++ b/wled00/const.h @@ -122,6 +122,8 @@ #define TYPE_NONE 0 //light is not configured #define TYPE_RESERVED 1 //unused. Might indicate a "virtual" light +#define TYPE_VIRTUAL_RGB 2 //virtual RGB bus (master broadcast bus) +#define TYPE_VIRTUAL_RGBW 3 //virtual RGBW bus (master broadcast bus) //Digital types (data pin only) (16-31) #define TYPE_WS2812_1CH 20 //white-only chips #define TYPE_WS2812_WWA 21 //amber + warm + cold white diff --git a/wled00/data/settings_leds.htm b/wled00/data/settings_leds.htm index 110fed77..50c44d07 100644 --- a/wled00/data/settings_leds.htm +++ b/wled00/data/settings_leds.htm @@ -1,459 +1,478 @@ - - - - - - LED Settings - - - - -
-
-
-
-
-

LED & Hardware setup

- Total LED count:
- Recommended power supply for brightest white:
- ?
-
-
- Enable automatic brightness limiter:
-
- Maximum Current: mA
- - Automatically limits brightness to stay close to the limit.
- Keep at <1A if powering LEDs directly from the ESP 5V pin!
- If you are using an external power supply, enter its rating.
- (Current estimated usage: unknown)


- LED voltage (Max. current for a single LED):
-
- - Keep at default if you are unsure about your type of LEDs.
-
-

Hardware setup

-
LED outputs:
- -
- LED Memory Usage: 0 / ? B
-

- - Make a segment for each output:
-
-
- Touch threshold:
- IR GPIO:  ×
- -
- IR info
- Relay GPIO: invert  ×
-
-

Defaults

- Turn LEDs on after power up/reset:
- Default brightness: (0-255)

- Apply preset at boot (0 uses defaults) -

- Use Gamma correction for color: (strongly recommended)
- Use Gamma correction for brightness: (not recommended)

- Brightness factor: % -

Transitions

- Crossfade:
- Transition Time: ms
- Enable Palette transitions: -

Timed light

- Default Duration: min
- Default Target brightness:
- Mode: - -

Advanced

- Palette blending: -
- - Auto-calculate white channel from RGB:
- -

- -
- - + + + + + + LED Settings + + + + +
+
+
+
+
+

LED & Hardware setup

+ Total LED count:
+ Recommended power supply for brightest white:
+ ?
+
+
+ Enable automatic brightness limiter:
+
+ Maximum Current: mA
+ + Automatically limits brightness to stay close to the limit.
+ Keep at <1A if powering LEDs directly from the ESP 5V pin!
+ If you are using an external power supply, enter its rating.
+ (Current estimated usage: unknown)


+ LED voltage (Max. current for a single LED):
+
+ + Keep at default if you are unsure about your type of LEDs.
+
+

Hardware setup

+
LED outputs:
+
+ +
+ LED Memory Usage: 0 / ? B
+

+ +
+ Create a segment for each output:
+
+
+ Touch threshold:
+ IR GPIO:  ×
+ +
+ IR info
+ Relay GPIO: invert  ×
+
+

Defaults

+ Turn LEDs on after power up/reset:
+ Default brightness: (0-255)

+ Apply preset at boot (0 uses defaults) +

+ Use Gamma correction for color: (strongly recommended)
+ Use Gamma correction for brightness: (not recommended)

+ Brightness factor: % +

Transitions

+ Crossfade:
+ Transition Time: ms
+ Enable Palette transitions: +

Timed light

+ Default Duration: min
+ Default Target brightness:
+ Mode: + +

Advanced

+ Palette blending: +
+ + Auto-calculate white channel from RGB:
+ +

+ +
+ + diff --git a/wled00/fcn_declare.h b/wled00/fcn_declare.h index 06f80cfc..3556bbd2 100644 --- a/wled00/fcn_declare.h +++ b/wled00/fcn_declare.h @@ -197,6 +197,7 @@ bool updateVal(const String* req, const char* key, byte* val, byte minv=0, byte //udp.cpp void notify(byte callMode, bool followUp=false); +void realtimeBoroadcast(IPAddress client, uint16_t length, byte *buffer, bool isRGBW); void realtimeLock(uint32_t timeoutMs, byte md = REALTIME_MODE_GENERIC); void handleNotifications(); void setRealtimePixel(uint16_t i, byte r, byte g, byte b, byte w); diff --git a/wled00/html_settings.h b/wled00/html_settings.h index 1b267892..3da5145b 100644 --- a/wled00/html_settings.h +++ b/wled00/html_settings.h @@ -77,15 +77,15 @@ onclick="B()">Back // Autogenerated from wled00/data/settings_leds.htm, do not edit!! const char PAGE_settings_leds[] PROGMEM = R"=====(LED Settings