Added support for GBR, BGR. Tweaked README.

This commit is contained in:
KurtMF
2024-12-12 13:43:33 -05:00
parent 58cea25f25
commit 063d4b3278
4 changed files with 64 additions and 27 deletions
+2 -2
View File
@@ -58,9 +58,9 @@
#define CORDER_RGB 0 //* WS2811, YF923
#define CORDER_RBG 1
#define CORDER_GRB 2 //* WS2811B, Most LED strips are wired this way
#define CORDER_GBR 3
#define CORDER_GBR 3 //*
#define CORDER_BRG 4 //* Adafruit Product ID: 5984 As of November 5, 2024 - this strand has different 'internal' color ordering. It's now BRG not RGB,
#define CORDER_BGR 5 // Adafruit Dotstar LEDs SK9822 uses this CO but they use inverted start/stop bits
#define CORDER_BGR 5 //* Adafruit Dotstar LEDs SK9822 uses this CO but they use inverted start/stop bits
#define CORDER_RGBW 6 //* Popular
#define CORDER_RBGW 7
#define CORDER_GRBW 8
+47 -6
View File
@@ -52,6 +52,7 @@ GOIO9List = { 2, 3, 4, 5, 29, 33, 48, 49, 50, 51, 52, 53, 54 } //6 top, 7 botto
* Added setBrightness(), setBalance()
* FrameBuffer no longer passed in, constructor now creates buffer; destructor added
* Added support for per-object setting of OC factor, TH+TL, T0H, T1H, and LATCH_DELAY in begin function
* Set DSE=3, SPEED=0, SRE=0 on output pins per experiment & PJRC forum guidance
*/
#ifndef __IMXRT1062__
@@ -303,6 +304,22 @@ void ObjectFLED::genFrameBuffer(uint32_t serp) {
j += 3;
} //for(leds in drawbuffer)
break;
case CORDER_GBR:
for (uint16_t i = 0; i < (numbytes * numpins); i += 3) {
*(frameBuffer + i + 2) = *((uint8_t*)drawBuffer + j) * rLevel / 65025;
*(frameBuffer + i) = *((uint8_t*)drawBuffer + j + 1) * gLevel / 65025;
*(frameBuffer + i + 1) = *((uint8_t*)drawBuffer + j + 2) * bLevel / 65025;
j += 3;
} //for(leds in drawbuffer)
break;
case CORDER_BGR:
for (uint16_t i = 0; i < (numbytes * numpins); i += 3) {
*(frameBuffer + i + 2) = *((uint8_t*)drawBuffer + j) * rLevel / 65025;
*(frameBuffer + i + 1) = *((uint8_t*)drawBuffer + j + 1) * gLevel / 65025;
*(frameBuffer + i) = *((uint8_t*)drawBuffer + j + 2) * bLevel / 65025;
j += 3;
} //for(leds in drawbuffer)
break;
case CORDER_BRG:
for (uint16_t i = 0; i < (numbytes * numpins); i += 3) {
*(frameBuffer + i + 1) = *((uint8_t*)drawBuffer + j) * rLevel / 65025;
@@ -346,6 +363,30 @@ void ObjectFLED::genFrameBuffer(uint32_t serp) {
j += jChange;
} //for(leds in drawbuffer)
break;
case CORDER_GBR:
for (uint16_t i = 0; i < (numbytes * numpins); i += 3) {
if (i % (serp * 3) == 0) {
if (jChange < 0) { j = i; jChange = 3; }
else { j = i + (serp - 1) * 3; jChange = -3; }
}
*(frameBuffer + i + 2) = *((uint8_t*)drawBuffer + j) * rLevel / 65025;
*(frameBuffer + i) = *((uint8_t*)drawBuffer + j + 1) * gLevel / 65025;
*(frameBuffer + i + 1) = *((uint8_t*)drawBuffer + j + 2) * bLevel / 65025;
j += 3;
} //for(leds in drawbuffer)
break;
case CORDER_BGR:
for (uint16_t i = 0; i < (numbytes * numpins); i += 3) {
if (i % (serp * 3) == 0) {
if (jChange < 0) { j = i; jChange = 3; }
else { j = i + (serp - 1) * 3; jChange = -3; }
}
*(frameBuffer + i + 2) = *((uint8_t*)drawBuffer + j) * rLevel / 65025;
*(frameBuffer + i + 1) = *((uint8_t*)drawBuffer + j + 1) * gLevel / 65025;
*(frameBuffer + i) = *((uint8_t*)drawBuffer + j + 2) * bLevel / 65025;
j += 3;
} //for(leds in drawbuffer)
break;
case CORDER_BRG:
for (uint16_t i = 0; i < (numbytes * numpins); i += 3) {
if (i % (serp * 3) == 0) {
@@ -541,17 +582,17 @@ int ObjectFLED::busy(void)
void ObjectFLED::setBrightness(uint8_t brightLevel) {
brightness = brightLevel;
rLevel = (brightness + 1) * (colorBalance >> 16);
gLevel = (brightness + 1) * ((colorBalance >> 8) & 0xFF);
bLevel = (brightness + 1) * (colorBalance & 0xFF);
rLevel = brightness * (colorBalance >> 16);
gLevel = brightness * ((colorBalance >> 8) & 0xFF);
bLevel = brightness * (colorBalance & 0xFF);
}
void ObjectFLED::setBalance(uint32_t balMask) {
colorBalance = balMask & 0xFFFFFF;
rLevel = (brightness + 1) * (colorBalance >> 16);
gLevel = (brightness + 1) * ((colorBalance >> 8) & 0xFF);
bLevel = (brightness + 1) * (colorBalance & 0xFF);
rLevel = brightness * (colorBalance >> 16);
gLevel = brightness * ((colorBalance >> 8) & 0xFF);
bLevel = brightness * (colorBalance & 0xFF);
}
+14 -18
View File
@@ -1,9 +1,8 @@
# ObjectFLED.h
Allows for configuration and control of multiple (physical) digital LED display objects
FastLED-friendly LED display driver allows for configuration and control of multiple digital LED display devices
independently in code. Display objects use DMA transfer (from [OctoWS2811 library](http://www.pjrc.com/teensy/td_libs_OctoWS2811.html))
on any or all 40 or 55 pins of Teensy 4.0 or 4.1 to drive digital LEDs with massive parallelism,
if needed.
on any or all 40 or 55 pins of Teensy 4.0 or 4.1 to drive digital LEDs with massive parallelism.
The show() function is non-blocking, returning control to the graphics drawing code in just 6% of
the time it takes to complete buffer transmission to an LED string (tested with WS2812B, 1.6
@@ -22,7 +21,7 @@ planes of a cube, a single string of house lights, an orbit of an electron, etc.
- For Teensy 4.x only. It may be possible to add other boards if they support DMA driven by
configurable timers, and ability to map digital pins to a data register which DMA can target.
- LED data color formats: RGB, GRB, BRG, and RGBW
- LED data color formats: RGB, GRB, BRG, GBR, BGR and RGBW
## MAIN BENEFITS
@@ -30,7 +29,7 @@ planes of a cube, a single string of house lights, an orbit of an electron, etc.
* You can independently configure, control and display multiple LED devices connected to your
Teensy 4.x, even if the devices use different LED types with different specs. Combine LED devices
into a single display object, or define separate objects for segments of each device, or just plain
one display object for each device (segmentation is automatic). It is also possible to define 2
one display object for each device. It is also possible to define 2
display objects to display the same drawing buffer on 2 different LED devices.
* Large LED devices can be driven with parallel output to separate segments of the device. Physical
@@ -45,21 +44,12 @@ bytes per LED in RGB order.
* You can tweak the shape of the LED data waveform generated by this driver. By calling begin()
with full pulse timing specs, you can tweak the waveform to achieve the highest possible overclock
(and highest back-to-back refresh rate). Each display object has it's own begin() function, and
it's own LED timing.
* The show() function is non-blocking, and returns in just 6% of the time required to write a single
segment. However when calling show() back-to-back, each must wait for the prior to complete it's
latch pulse at the end of writing. This is also true when calling show() for one object right after
calling show() for another object. All display objects share the same DMA-Timer pipeline in hardware.
Therefore, for code which controls a large LED device and a small one, with sequential calls to each
show(): show the small one first, then show the large one, then update your drawing while the large
display is still DMA-transmitting 94% of it's LED data.
(and highest back-to-back refresh rate).
* Show() function has built-in handling for serpentine, color order, brightness, and color balance
for each object. Like in FastLED, these are applied to the frame buffer, not your drawing buffer.
Get and set functions for brightness and colormask are included (the ones in FastLED won't work on
ObjectFLED display objects).
ObjectFLED display objects). These are applied independently to each display object in your sketch.
* Accessory functions included to fade a drawing array to a color other than black, and to draw a
square on an LED plane.
@@ -78,7 +68,8 @@ level).
When taking advantage of parallel inputs into an LED device, each pin is assumed to drive the same
number of LEDs (or rows or planes). When you define your ObjectFLED object, provide an ordered pin
list which matches the order in which the pins connect to the device. ObjectFLED will output segments from your display buffer to those pins in the order you specify.
list which matches the order in which the pins connect to the device. ObjectFLED will output
segments from your display buffer to those pins in the order you specify, and simultaneously.
Individual LEDs come with various formats for RGB color order, data signal clock frequency, and
pulse timing specs. ObjectFLED defaults will work for popular RGB-order LEDs with 800KHz clock and
@@ -152,7 +143,12 @@ NOTE: In test I had to use 72uS latch delay for LEDs with a spec of 50uS, in ord
### show() FUNCTION
See MAIN BENEFITS above for details.
See MAIN BENEFITS above for details. When calling show() back-to-back, each must wait for the prior to complete it's
latch pulse at the end of writing. This is also true when calling show() for one object right after
calling show() for another object. All display objects share the same DMA-Timer pipeline in hardware.
Therefore, for code which controls a large LED device and a small one, with sequential calls to each
show(): show the small one first, then show the large one, then update your drawing while the large
display is still DMA-transmitting 94% of it's LED data.
**Example:**
+1 -1
View File
@@ -1,5 +1,5 @@
name=ObjectFLED
version=1.0.2
version=1.0.3
author=Kurt Funderburg
maintainer=Kurt Funderburg
sentence=Independently configure and display to various LED devices in one sketch with parallel DMA-driven LED output.