Global buffer and ABL fixes
This commit is contained in:
parent
f6e86bfcf8
commit
61ba16b779
@ -1209,7 +1209,13 @@ uint8_t WS2812FX::estimateCurrentAndLimitBri() {
|
|||||||
uint16_t len = bus->getLength();
|
uint16_t len = bus->getLength();
|
||||||
uint32_t busPowerSum = 0;
|
uint32_t busPowerSum = 0;
|
||||||
for (uint_fast16_t i = 0; i < len; i++) { //sum up the usage of each LED
|
for (uint_fast16_t i = 0; i < len; i++) { //sum up the usage of each LED
|
||||||
uint32_t c = bus->getPixelColor(i);
|
uint32_t c = 0;
|
||||||
|
if (_globalLedBuffer)
|
||||||
|
{
|
||||||
|
c = _globalLedBuffer[bus->getStart() + i];
|
||||||
|
} else {
|
||||||
|
c = bus->getPixelColor(i);
|
||||||
|
}
|
||||||
byte r = R(c), g = G(c), b = B(c), w = W(c);
|
byte r = R(c), g = G(c), b = B(c), w = W(c);
|
||||||
|
|
||||||
if(useWackyWS2815PowerModel) { //ignore white component on WS2815 power calculation
|
if(useWackyWS2815PowerModel) { //ignore white component on WS2815 power calculation
|
||||||
@ -1253,6 +1259,7 @@ void WS2812FX::show(void) {
|
|||||||
show_callback callback = _callback;
|
show_callback callback = _callback;
|
||||||
if (callback) callback();
|
if (callback) callback();
|
||||||
|
|
||||||
|
Bus::setRestoreBri(_renderBrightness);
|
||||||
uint8_t busBrightness = estimateCurrentAndLimitBri();
|
uint8_t busBrightness = estimateCurrentAndLimitBri();
|
||||||
|
|
||||||
if (_globalLedBuffer) { // copy data from buffer to bus
|
if (_globalLedBuffer) { // copy data from buffer to bus
|
||||||
@ -1260,7 +1267,8 @@ void WS2812FX::show(void) {
|
|||||||
} else {
|
} else {
|
||||||
// if brightness changed since last show, must set everything again to update to new luminance
|
// if brightness changed since last show, must set everything again to update to new luminance
|
||||||
if (_renderBrightness != busBrightness) {
|
if (_renderBrightness != busBrightness) {
|
||||||
for (uint16_t i = 0; i < _length; i++) busses.setPixelColor(i, busses.getPixelColor(i)); // LOSSY and slow!
|
for (uint16_t i = 0; i < _length; i++) busses.setPixelColor(i, busses.getPixelColor(i)); // LOSSLESS due to trick (but still slow!)
|
||||||
|
Bus::setRestoreBri(busBrightness);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1343,6 +1351,7 @@ void WS2812FX::setBrightness(uint8_t b, bool direct) {
|
|||||||
// would be dangerous if applied immediately (could exceed ABL), but will not output until the next show()
|
// would be dangerous if applied immediately (could exceed ABL), but will not output until the next show()
|
||||||
busses.setBrightness(b);
|
busses.setBrightness(b);
|
||||||
_renderBrightness = b;
|
_renderBrightness = b;
|
||||||
|
Bus::setRestoreBri(b);
|
||||||
} else {
|
} else {
|
||||||
unsigned long t = millis();
|
unsigned long t = millis();
|
||||||
if (_segments[0].next_time > t + 22 && t - _lastShow > MIN_SHOW_DELAY) show(); //apply brightness change immediately if no refresh soon
|
if (_segments[0].next_time > t + 22 && t - _lastShow > MIN_SHOW_DELAY) show(); //apply brightness change immediately if no refresh soon
|
||||||
|
@ -563,3 +563,4 @@ uint16_t BusManager::getTotalLength() {
|
|||||||
int16_t Bus::_cct = -1;
|
int16_t Bus::_cct = -1;
|
||||||
uint8_t Bus::_cctBlend = 0;
|
uint8_t Bus::_cctBlend = 0;
|
||||||
uint8_t Bus::_gAWM = 255;
|
uint8_t Bus::_gAWM = 255;
|
||||||
|
uint8_t Bus::_restaurationBri = 255;
|
||||||
|
@ -154,6 +154,7 @@ class Bus {
|
|||||||
inline uint8_t getAutoWhiteMode() { return _autoWhiteMode; }
|
inline uint8_t getAutoWhiteMode() { return _autoWhiteMode; }
|
||||||
inline static void setGlobalAWMode(uint8_t m) { if (m < 5) _gAWM = m; else _gAWM = AW_GLOBAL_DISABLED; }
|
inline static void setGlobalAWMode(uint8_t m) { if (m < 5) _gAWM = m; else _gAWM = AW_GLOBAL_DISABLED; }
|
||||||
inline static uint8_t getGlobalAWMode() { return _gAWM; }
|
inline static uint8_t getGlobalAWMode() { return _gAWM; }
|
||||||
|
inline static void setRestoreBri(uint8_t b) { _restaurationBri = b; }
|
||||||
|
|
||||||
bool reversed = false;
|
bool reversed = false;
|
||||||
|
|
||||||
@ -168,6 +169,7 @@ class Bus {
|
|||||||
static uint8_t _gAWM;
|
static uint8_t _gAWM;
|
||||||
static int16_t _cct;
|
static int16_t _cct;
|
||||||
static uint8_t _cctBlend;
|
static uint8_t _cctBlend;
|
||||||
|
static uint8_t _restaurationBri; // previous brightness used as setPixelColor was called. Used for lossy restoration
|
||||||
|
|
||||||
uint32_t autoWhiteCalc(uint32_t c);
|
uint32_t autoWhiteCalc(uint32_t c);
|
||||||
};
|
};
|
||||||
@ -231,7 +233,7 @@ class BusDigital : public Bus {
|
|||||||
for (uint8_t i=0; i<4; i++)
|
for (uint8_t i=0; i<4; i++)
|
||||||
{
|
{
|
||||||
uint16_t val = chan[i];
|
uint16_t val = chan[i];
|
||||||
chan[i] = (val << 8) / (_bri + 1);
|
chan[i] = ((val << 8) + _restaurationBri) / (_restaurationBri + 1); //adding _bri slighly improves recovery / stops degradation on re-scale
|
||||||
}
|
}
|
||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
|
@ -134,7 +134,8 @@ bool deserializeConfig(JsonObject doc, bool fromFS) {
|
|||||||
if (fromFS || !ins.isNull()) {
|
if (fromFS || !ins.isNull()) {
|
||||||
uint8_t s = 0; // bus iterator
|
uint8_t s = 0; // bus iterator
|
||||||
if (fromFS) busses.removeAll(); // can't safely manipulate busses directly in network callback
|
if (fromFS) busses.removeAll(); // can't safely manipulate busses directly in network callback
|
||||||
uint32_t mem = 0;
|
uint32_t mem = 0, globalBufMem = 0;
|
||||||
|
uint16_t maxlen = 0;
|
||||||
bool busesChanged = false;
|
bool busesChanged = false;
|
||||||
for (JsonObject elm : ins) {
|
for (JsonObject elm : ins) {
|
||||||
if (s >= WLED_MAX_BUSSES+WLED_MIN_VIRTUAL_BUSSES) break;
|
if (s >= WLED_MAX_BUSSES+WLED_MIN_VIRTUAL_BUSSES) break;
|
||||||
@ -162,7 +163,11 @@ bool deserializeConfig(JsonObject doc, bool fromFS) {
|
|||||||
if (fromFS) {
|
if (fromFS) {
|
||||||
BusConfig bc = BusConfig(ledType, pins, start, length, colorOrder, reversed, skipFirst, AWmode, freqkHz);
|
BusConfig bc = BusConfig(ledType, pins, start, length, colorOrder, reversed, skipFirst, AWmode, freqkHz);
|
||||||
mem += BusManager::memUsage(bc);
|
mem += BusManager::memUsage(bc);
|
||||||
if (mem <= MAX_LED_MEMORY) if (busses.add(bc) == -1) break; // finalization will be done in WLED::beginStrip()
|
if (strip.useGlobalLedBuffer && start + length > maxlen) {
|
||||||
|
maxlen = start + length;
|
||||||
|
globalBufMem = maxlen * 4;
|
||||||
|
}
|
||||||
|
if (mem + globalBufMem <= MAX_LED_MEMORY) if (busses.add(bc) == -1) break; // finalization will be done in WLED::beginStrip()
|
||||||
} else {
|
} else {
|
||||||
if (busConfigs[s] != nullptr) delete busConfigs[s];
|
if (busConfigs[s] != nullptr) delete busConfigs[s];
|
||||||
busConfigs[s] = new BusConfig(ledType, pins, start, length, colorOrder, reversed, skipFirst, AWmode);
|
busConfigs[s] = new BusConfig(ledType, pins, start, length, colorOrder, reversed, skipFirst, AWmode);
|
||||||
|
@ -141,7 +141,7 @@
|
|||||||
let len = parseInt(d.getElementsByName("LC"+n)[0].value);
|
let len = parseInt(d.getElementsByName("LC"+n)[0].value);
|
||||||
len += parseInt(d.getElementsByName("SL"+n)[0].value); // skipped LEDs are allocated too
|
len += parseInt(d.getElementsByName("SL"+n)[0].value); // skipped LEDs are allocated too
|
||||||
let dbl = 0;
|
let dbl = 0;
|
||||||
if (d.Sf.LD.checked) dbl = len * 3; // double buffering
|
if (d.Sf.LD.checked) dbl = len * 4; // double buffering
|
||||||
if (t < 32) {
|
if (t < 32) {
|
||||||
if (t==26 || t==29) len *= 2; // 16 bit LEDs
|
if (t==26 || t==29) len *= 2; // 16 bit LEDs
|
||||||
if (maxM < 10000 && d.getElementsByName("L0"+n)[0].value == 3) { //8266 DMA uses 5x the mem
|
if (maxM < 10000 && d.getElementsByName("L0"+n)[0].value == 3) { //8266 DMA uses 5x the mem
|
||||||
|
@ -151,11 +151,16 @@ void WLED::loop()
|
|||||||
DEBUG_PRINTLN(F("Re-init busses."));
|
DEBUG_PRINTLN(F("Re-init busses."));
|
||||||
bool aligned = strip.checkSegmentAlignment(); //see if old segments match old bus(ses)
|
bool aligned = strip.checkSegmentAlignment(); //see if old segments match old bus(ses)
|
||||||
busses.removeAll();
|
busses.removeAll();
|
||||||
uint32_t mem = 0;
|
uint32_t mem = 0, globalBufMem = 0;
|
||||||
|
uint16_t maxlen = 0;
|
||||||
for (uint8_t i = 0; i < WLED_MAX_BUSSES+WLED_MIN_VIRTUAL_BUSSES; i++) {
|
for (uint8_t i = 0; i < WLED_MAX_BUSSES+WLED_MIN_VIRTUAL_BUSSES; i++) {
|
||||||
if (busConfigs[i] == nullptr) break;
|
if (busConfigs[i] == nullptr) break;
|
||||||
mem += BusManager::memUsage(*busConfigs[i]);
|
mem += BusManager::memUsage(*busConfigs[i]);
|
||||||
if (mem <= MAX_LED_MEMORY) {
|
if (strip.useGlobalLedBuffer && busConfigs[i]->start + busConfigs[i]->count > maxlen) {
|
||||||
|
maxlen = busConfigs[i]->start + busConfigs[i]->count;
|
||||||
|
globalBufMem = maxlen * 4;
|
||||||
|
}
|
||||||
|
if (mem + globalBufMem <= MAX_LED_MEMORY) {
|
||||||
busses.add(*busConfigs[i]);
|
busses.add(*busConfigs[i]);
|
||||||
}
|
}
|
||||||
delete busConfigs[i]; busConfigs[i] = nullptr;
|
delete busConfigs[i]; busConfigs[i] = nullptr;
|
||||||
|
Loading…
Reference in New Issue
Block a user