Exclude virtual busses from current calculation (#2262)
This commit is contained in:
parent
8b2145bd88
commit
f4b47ed399
10
wled00/FX.h
10
wled00/FX.h
@ -682,6 +682,8 @@ class WS2812FX {
|
|||||||
ablMilliampsMax,
|
ablMilliampsMax,
|
||||||
currentMilliamps,
|
currentMilliamps,
|
||||||
triwave16(uint16_t),
|
triwave16(uint16_t),
|
||||||
|
getLengthTotal(void),
|
||||||
|
getLengthPhysical(void),
|
||||||
getFps();
|
getFps();
|
||||||
|
|
||||||
uint32_t
|
uint32_t
|
||||||
@ -841,9 +843,6 @@ class WS2812FX {
|
|||||||
|
|
||||||
uint16_t _cumulativeFps = 2;
|
uint16_t _cumulativeFps = 2;
|
||||||
|
|
||||||
void load_gradient_palette(uint8_t);
|
|
||||||
void handle_palette(void);
|
|
||||||
|
|
||||||
bool
|
bool
|
||||||
_triggered;
|
_triggered;
|
||||||
|
|
||||||
@ -877,7 +876,10 @@ class WS2812FX {
|
|||||||
|
|
||||||
void
|
void
|
||||||
blendPixelColor(uint16_t n, uint32_t color, uint8_t blend),
|
blendPixelColor(uint16_t n, uint32_t color, uint8_t blend),
|
||||||
startTransition(uint8_t oldBri, uint32_t oldCol, uint16_t dur, uint8_t segn, uint8_t slot);
|
startTransition(uint8_t oldBri, uint32_t oldCol, uint16_t dur, uint8_t segn, uint8_t slot),
|
||||||
|
estimateCurrentAndLimitBri(void),
|
||||||
|
load_gradient_palette(uint8_t),
|
||||||
|
handle_palette(void);
|
||||||
|
|
||||||
uint16_t* customMappingTable = nullptr;
|
uint16_t* customMappingTable = nullptr;
|
||||||
uint16_t customMappingSize = 0;
|
uint16_t customMappingSize = 0;
|
||||||
|
@ -259,12 +259,7 @@ void WS2812FX::setPixelColor(uint16_t i, byte r, byte g, byte b, byte w)
|
|||||||
#define MA_FOR_ESP 100 //how much mA does the ESP use (Wemos D1 about 80mA, ESP32 about 120mA)
|
#define MA_FOR_ESP 100 //how much mA does the ESP use (Wemos D1 about 80mA, ESP32 about 120mA)
|
||||||
//you can set it to 0 if the ESP is powered by USB and the LEDs by external
|
//you can set it to 0 if the ESP is powered by USB and the LEDs by external
|
||||||
|
|
||||||
void WS2812FX::show(void) {
|
void WS2812FX::estimateCurrentAndLimitBri() {
|
||||||
|
|
||||||
// avoid race condition, caputre _callback value
|
|
||||||
show_callback callback = _callback;
|
|
||||||
if (callback) callback();
|
|
||||||
|
|
||||||
//power limit calculation
|
//power limit calculation
|
||||||
//each LED can draw up 195075 "power units" (approx. 53mA)
|
//each LED can draw up 195075 "power units" (approx. 53mA)
|
||||||
//one PU is the power it takes to have 1 channel 1 step brighter per brightness step
|
//one PU is the power it takes to have 1 channel 1 step brighter per brightness step
|
||||||
@ -277,41 +272,44 @@ void WS2812FX::show(void) {
|
|||||||
actualMilliampsPerLed = 12; // from testing an actual strip
|
actualMilliampsPerLed = 12; // from testing an actual strip
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ablMilliampsMax > 149 && actualMilliampsPerLed > 0) //0 mA per LED and too low numbers turn off calculation
|
if (ablMilliampsMax < 150 || actualMilliampsPerLed == 0) { //0 mA per LED and too low numbers turn off calculation
|
||||||
{
|
currentMilliamps = 0;
|
||||||
|
busses.setBrightness(_brightness);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint16_t pLen = getLengthPhysical();
|
||||||
uint32_t puPerMilliamp = 195075 / actualMilliampsPerLed;
|
uint32_t puPerMilliamp = 195075 / actualMilliampsPerLed;
|
||||||
uint32_t powerBudget = (ablMilliampsMax - MA_FOR_ESP) * puPerMilliamp; //100mA for ESP power
|
uint32_t powerBudget = (ablMilliampsMax - MA_FOR_ESP) * puPerMilliamp; //100mA for ESP power
|
||||||
if (powerBudget > puPerMilliamp * _length) //each LED uses about 1mA in standby, exclude that from power budget
|
if (powerBudget > puPerMilliamp * pLen) { //each LED uses about 1mA in standby, exclude that from power budget
|
||||||
{
|
powerBudget -= puPerMilliamp * pLen;
|
||||||
powerBudget -= puPerMilliamp * _length;
|
} else {
|
||||||
} else
|
|
||||||
{
|
|
||||||
powerBudget = 0;
|
powerBudget = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t powerSum = 0;
|
uint32_t powerSum = 0;
|
||||||
|
|
||||||
for (uint16_t i = 0; i < _length; i++) //sum up the usage of each LED
|
for (uint8_t b = 0; b < busses.getNumBusses(); b++) {
|
||||||
{
|
Bus *bus = busses.getBus(b);
|
||||||
uint32_t c = busses.getPixelColor(i);
|
if (bus->getType() >= TYPE_NET_DDP_RGB) continue; //exclude non-physical network busses
|
||||||
|
uint16_t len = bus->getLength();
|
||||||
|
uint32_t busPowerSum = 0;
|
||||||
|
for (uint16_t i = 0; i < len; i++) { //sum up the usage of each LED
|
||||||
|
uint32_t c = bus->getPixelColor(i);
|
||||||
byte r = c >> 16, g = c >> 8, b = c, w = c >> 24;
|
byte r = c >> 16, g = c >> 8, b = c, w = c >> 24;
|
||||||
|
|
||||||
if(useWackyWS2815PowerModel)
|
if(useWackyWS2815PowerModel) { //ignore white component on WS2815 power calculation
|
||||||
{
|
busPowerSum += (MAX(MAX(r,g),b)) * 3;
|
||||||
// ignore white component on WS2815 power calculation
|
} else {
|
||||||
powerSum += (MAX(MAX(r,g),b)) * 3;
|
busPowerSum += (r + g + b + w);
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
powerSum += (r + g + b + w);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (bus->isRgbw()) { //RGBW led total output with white LEDs enabled is still 50mA, so each channel uses less
|
||||||
if (isRgbw) //RGBW led total output with white LEDs enabled is still 50mA, so each channel uses less
|
busPowerSum *= 3;
|
||||||
{
|
busPowerSum = busPowerSum >> 2; //same as /= 4
|
||||||
powerSum *= 3;
|
}
|
||||||
powerSum = powerSum >> 2; //same as /= 4
|
powerSum += busPowerSum;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t powerSum0 = powerSum;
|
uint32_t powerSum0 = powerSum;
|
||||||
@ -323,20 +321,24 @@ void WS2812FX::show(void) {
|
|||||||
uint16_t scaleI = scale * 255;
|
uint16_t scaleI = scale * 255;
|
||||||
uint8_t scaleB = (scaleI > 255) ? 255 : scaleI;
|
uint8_t scaleB = (scaleI > 255) ? 255 : scaleI;
|
||||||
uint8_t newBri = scale8(_brightness, scaleB);
|
uint8_t newBri = scale8(_brightness, scaleB);
|
||||||
busses.setBrightness(newBri);
|
busses.setBrightness(newBri); //to keep brightness uniform, sets virtual busses too
|
||||||
currentMilliamps = (powerSum0 * newBri) / puPerMilliamp;
|
currentMilliamps = (powerSum0 * newBri) / puPerMilliamp;
|
||||||
} else
|
} else {
|
||||||
{
|
|
||||||
currentMilliamps = powerSum / puPerMilliamp;
|
currentMilliamps = powerSum / puPerMilliamp;
|
||||||
busses.setBrightness(_brightness);
|
busses.setBrightness(_brightness);
|
||||||
}
|
}
|
||||||
currentMilliamps += MA_FOR_ESP; //add power of ESP back to estimate
|
currentMilliamps += MA_FOR_ESP; //add power of ESP back to estimate
|
||||||
currentMilliamps += _length; //add standby power back to estimate
|
currentMilliamps += pLen; //add standby power back to estimate
|
||||||
} else {
|
|
||||||
currentMilliamps = 0;
|
|
||||||
busses.setBrightness(_brightness);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void WS2812FX::show(void) {
|
||||||
|
|
||||||
|
// avoid race condition, caputre _callback value
|
||||||
|
show_callback callback = _callback;
|
||||||
|
if (callback) callback();
|
||||||
|
|
||||||
|
estimateCurrentAndLimitBri();
|
||||||
|
|
||||||
// some buses send asynchronously and this method will return before
|
// some buses send asynchronously and this method will return before
|
||||||
// all of the data has been sent.
|
// all of the data has been sent.
|
||||||
// See https://github.com/Makuna/NeoPixelBus/wiki/ESP32-NeoMethods#neoesp32rmt-methods
|
// See https://github.com/Makuna/NeoPixelBus/wiki/ESP32-NeoMethods#neoesp32rmt-methods
|
||||||
@ -553,6 +555,20 @@ uint32_t WS2812FX::getLastShow(void) {
|
|||||||
return _lastShow;
|
return _lastShow;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint16_t WS2812FX::getLengthTotal(void) {
|
||||||
|
return _length;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint16_t WS2812FX::getLengthPhysical(void) {
|
||||||
|
uint16_t len = 0;
|
||||||
|
for (uint8_t b = 0; b < busses.getNumBusses(); b++) {
|
||||||
|
Bus *bus = busses.getBus(b);
|
||||||
|
if (bus->getType() >= TYPE_NET_DDP_RGB) continue; //exclude non-physical network busses
|
||||||
|
len += bus->getLength();
|
||||||
|
}
|
||||||
|
return len;
|
||||||
|
}
|
||||||
|
|
||||||
void WS2812FX::setSegment(uint8_t n, uint16_t i1, uint16_t i2, uint8_t grouping, uint8_t spacing) {
|
void WS2812FX::setSegment(uint8_t n, uint16_t i1, uint16_t i2, uint8_t grouping, uint8_t spacing) {
|
||||||
if (n >= MAX_NUM_SEGMENTS) return;
|
if (n >= MAX_NUM_SEGMENTS) return;
|
||||||
Segment& seg = _segments[n];
|
Segment& seg = _segments[n];
|
||||||
|
Loading…
Reference in New Issue
Block a user