FAB_LED addressable LED library

I’m writing a LED library from scratch, focussing on performance and code compactness.
As is now, I estimate FAB_LED uses about 4X less memory than Adafruit and FastLED libraries.

I’m looking for folks willing to try it out and give me feedback.

It can be uploaded from:


I believe it’ll be easier to use and more powerful than FastLED or Adafruit’s neopixel libraries,
while at the same time consuming less memory, once I’m done.

Right now it supports ws2812, apa104, apa106 and sk6812 LEDs.
I’ve added apa102 (SPI) support but it’s yet untested.

I am also working on making it compatible with ARM CPUs (like Teensy 3.2), but I’m not quite there yet.

I also have in the plans support for 2D displays and sprites.

Palette support for 2, 4, 16 and 256 colors is there but I still need to polish it up.

User code can be relatively simple: The pixel array is not embedded in the LED class,
so you can manipulate any way you want easily. The code becomes natural.

#include <FAB_LED.h>

// FAB_LED provides many types of LEDs, here we use a WS2812B LED protocol on port D6
ws2812b<D,6> myLedStrip;

// grb is provided by FAB_LED for convenience. WS2812B natively uses GRB LEDs.
// other LED types include rgb, grbw, rgbw, bgr… You can also use uint8_t or uint32_t.
grb pixels[8] = {};

void setup() {

void loop() {
uint16_t pos = random(8 );
pixels[pos].r = random(16);
pixels[pos].g = random(16);
pixels[pos].b = random(16);

// You fully manage your array (unlike other LED libraries which embed it
// into their class), and just send it when you’re ready to show it.
myLedStrip.sendPixels(8, pixels);


Yea, so I know this post is super old but I am looking for a library that will work with teensy 3.6’s audio library (which uses interrupts that interfere with the adafruit neopixel library) and also supports rgbw sk6812’s. It appears as though your library would work, but I’m just not getting anything. If you have any suggestions I would appreciate them. Simply nothing is happening, so I’m not sure what to do. Is it possible that I cannot use pin 29 to send data?

Here’s the strips that I’m using. There are two, back to back, with the data lines in parallel, so essentially only 144 leds to address. Adafruit NeoPixel Digital RGBW LED Strip - White PCB 144 LED/m [1m] : ID 2847 : $69.95 : Adafruit Industries, Unique & fun DIY electronics and kits

//////////////////////////LIBRARIES AND VARIABLES////////////////////////////
#include <Audio.h>
#include <Wire.h>
#include <SPI.h>
#include <SD.h>
#include <SerialFlash.h>
//#include <Adafruit_NeoPixel.h>
#include <FAB_LED.h>

const int ledPin = 13;

//initialize button
#define primaryButton 31

//blade status
int activated = 0;
int prevState = 0;
int bladeDelay = 1; //delay between led ignition

//number leds
const uint8_t nLeds = 144;
const uint8_t nPin = 29;
//power factor
const uint8_t pf = 4;
//Default colors (preset 0):
const uint8_t red = 0;
const uint8_t green = 0;
const uint8_t blue = 0;
const uint8_t white = 255;
//Adafruit_NeoPixel blade = Adafruit_NeoPixel(nLeds, nPin, NEO_RGBW + NEO_KHZ800);
//uint32_t colorOn = blade.Color(green/pf, red/pf, blue/pf, white/pf);
//uint32_t colorOff = blade.Color(0,0,0,0);

sk6812b<D,nPin>  blade;
const uint8_t maxBrightness = 16; //max 255
const uint8_t numPixels = 144;
grbw  pixels[numPixels] = {};

////////////////////////////////AUDIO SETUP//////////////////////////////////
// GUItool: begin automatically generated code
AudioPlaySdWav           playSdWav1;     //xy=363.3333435058594,1350.333251953125
AudioPlaySdWav           playSdWav7;     //xy=362.75,1674.75
AudioPlaySdWav           playSdWav2;     //xy=366.3333435058594,1411.333251953125
AudioPlaySdWav           playSdWav5;     //xy=374.3333435058594,1569.333251953125
AudioPlaySdWav           playSdWav4;     //xy=375.3333435058594,1518.333251953125
AudioPlaySdWav           playSdWav6;     //xy=376.3333435058594,1619.333251953125
AudioPlaySdWav           playSdWav3;     //xy=377.3333435058594,1465.333251953125
AudioMixer4              mixer2;         //xy=806.3333435058594,1618.333251953125
AudioMixer4              mixer1;         //xy=816.3333435058594,1410.333251953125
AudioOutputAnalog        dac1;           //xy=1082.3333435058594,1412.333251953125
AudioConnection          patchCord1(playSdWav1, 0, mixer1, 0);
AudioConnection          patchCord2(playSdWav7, 0, mixer2, 3);
AudioConnection          patchCord3(playSdWav2, 0, mixer1, 1);
AudioConnection          patchCord4(playSdWav5, 0, mixer2, 1);
AudioConnection          patchCord5(playSdWav4, 0, mixer2, 0);
AudioConnection          patchCord6(playSdWav6, 0, mixer2, 2);
AudioConnection          patchCord7(playSdWav3, 0, mixer1, 2);
AudioConnection          patchCord8(mixer2, 0, mixer1, 3);
AudioConnection          patchCord9(mixer1, dac1);
// GUItool: end automatically generated code

float volumeGain = 4; //volume control variable

////////////////////////////////SDCARD SETUP/////////////////////////////////
// Use these with the Teensy Audio Shield
//#define SDCARD_CS_PIN    10
//#define SDCARD_MOSI_PIN  7
//#define SDCARD_SCK_PIN   14

// Use these with the Teensy 3.5 & 3.6 SD card
#define SDCARD_MOSI_PIN  11  // not actually used
#define SDCARD_SCK_PIN   13  // not actually used

// Use these for the SD+Wiz820 or other adaptors
//#define SDCARD_CS_PIN    4
//#define SDCARD_MOSI_PIN  11
//#define SDCARD_SCK_PIN   13

void setup()
  Serial.begin(115200);    //initialize serial communication
  AudioMemory(16); //set memory allocated to audio functions
  dac1.analogReference(EXTERNAL); //much louder!
  delay(50);             //time for DAC voltage stabilization
  pinMode(5, OUTPUT);
  digitalWrite(5, HIGH); // turn on the amplifier
  SPI.setMOSI(SDCARD_MOSI_PIN);   //set SD card MOSI pin
  SPI.setSCK(SDCARD_SCK_PIN);     //set SD card clock pin

  //return error if SD card cannot be accessed
  if (!(SD.begin(SDCARD_CS_PIN)))
    while (1) {
      Serial.println("Unable to access the SD card");

  pinMode(ledPin, OUTPUT); //board indicator LED

  //Set the gain on one of the mixer's channels. Input "channel" must be 0 to 3.
  //Input "level" may be any floating point number from 0.00004 to 32768.0.
  //The default is 1.0.
  //Values less than 1.0 attenuate the inputs, and values greater than 1.0 cause amplification.
  mixer1.gain(0, volumeGain * .25); //sdwav1
  mixer1.gain(1, volumeGain * .25); //sdwav2
  mixer1.gain(2, volumeGain * .25); //sdwav3
  mixer2.gain(0, volumeGain * .25); //sdwav4
  mixer2.gain(1, volumeGain * .25); //sdwav5
  mixer2.gain(2, volumeGain * .25); //sdwav6
  mixer2.gain(3, volumeGain * .25); //sdwav7

  //setup button
  pinMode(primaryButton, INPUT_PULLUP);

  //neopixel start
//  blade.begin();
//  blade.show();
  blade.clear(2 * numPixels);

void updateColors(char r, char g, char b, char w)
  for(int i = 0; i < numPixels; i++)
    pixels[i].r = r;
    pixels[i].g = g;
    pixels[i].b = b;
    pixels[i].w = w;

void loop() 
      digitalWrite(ledPin, HIGH);
      activated = 1;
      // Write the pixel array green
      updateColors(0, maxBrightness, 0, 0);
      // Display the pixels on the LED strip
      blade.sendPixels(numPixels, pixels);
      // Wait 0.1 seconds
//      for(byte i=0; i<nLeds; i++)
//      {
//          blade.setPixelColor(i,colorOn);
//          blade.show();
//          delay(bladeDelay);
//      }
    }else if(activated==1&&prevState==0)
      digitalWrite(ledPin, LOW);
      delay(25); //prevents some weird clipping that happens when the sounds are played back to back
      activated = 0;
      // Write the pixel array green
      updateColors(0, 0, 0, 0);
      // Display the pixels on the LED strip
      blade.sendPixels(numPixels, pixels);
      // Wait 0.1 seconds
//      for(byte i=nLeds; i>=0; i--)
//      {
//          blade.setPixelColor(i,colorOff);
//          blade.show();
//          delay(bladeDelay);
//      }
    //do nothing