The Noiasca Tool Kit for LEDs

The Noiasca Tool Kit contains several classes: It all starts with helpers to let LEDs blink, dim, flicker and several other effects in parallel without the usage of any delay. Furthermore the tool kit contains a class to read and debounce a button click very easily. Finally, the tool kit brings timers, which can be used to start and stop actions. For example if you want to start a blinking LED on button press and let it blink for 10 seconds, just combine a blink LED, the button and a timer from the Noiasca Tool Kit.

The Noiasca Tool Kit contains several classes for different style of LEDs. Each kind of pattern is explained here. Furthermore you are not limited to use the Arduino pins only, you can use this classes also for your WS2812 Neopixels.

On this page only the LED classes are explained in detail, but you will find a lot of examples for buttons and timer in the library examples.

This is a simple class to "blink" a LED. You can define the on and the off interval separately.

A very simple sketch to blink without delay will look like following:

#include <Noiasca_led.h>
#include <utility/Noiasca_discrete.h>

BlinkPin blinkLed {13};              // declare one blinking LED and assign pin 13

void setup() {
  blinkLed.begin();                  // you have to call the .begin() method for this LED
  //blinkLed.setInterval(700, 300);  // optional: you can define the ON and OFF times in milliseconds
  blinkLed.on();                     // switch the blinking on
}

void loop() {
  blinkLed.update();                 // call the update function in loop() to refresh the LED
  // put other non blocking code here, to run repeatedly
}

You need two #includes:
The library with the effects/patterns and the hardware interface. As we are using the pin 13 on the Arduino, we have to include the hardware interface for "discrete Arduino pins".

The constructor makes one blinking LED available on pin 13.

.begin() : The begin() must be called in setup(). It will do all hardware specific tasks. In the case of the blink LED it will set the pinMode to OUTPUT.

.on() will switch the blink effect on.

.update() will do all the magic behind the scenes. It works similar to "Blink without Delay". The class has it's own time management and will switch the pin on or off if it is needed.

There are several other member functions available for the blink LED:

.off() will switch off the effect - the LED will get dark.

.toggle() will either switch the effect on or off. This member function comes very handy when you have a single push button and if you want to switch the blinking on or off with each button press.

.setOnInterval(interval) and .setOffInterval(interval) with these member function you can define the on and off times. The default values are 500ms which give you a consistent blinking. If you want a flashing effect, you can make the one interval time longer than the other:

  blinkLed.setOnInterval(700);                // 700ms on
  blinkLed.setOffInterval(300);               // 300ms off

Alternating

"Alternating" is the blinking of two LEDs vice versa. Either the first or the second LED is on. The constructor of an alternating LED pair needs two pins:

AlternatingPin alternatingLed {2, 4}; 

Bounce5

"Bounce 5" is a LED pattern, with 5 LEDs: Only one LED is on and the other LEDs will be off. This gives an effect of a running LED between left and right. You can compare the effect with the  KITT/Larson Scanner. The constructor for this effect needs 5 pins:

Bounce5Pin bounce5led {2, 3, 4, 5, 6};

Flicker

This effect simulates a "flickering" light like a fire. The pattern is random and you will get an even better effect if you start flicker with two LEDs for example a red and a yellow LED. The effect should run on a PWM enabled pin:

FlickerPin flickerLed {3}; // UNO PWM pins 3, 5, 6, 9, 10, 11

Fluorescent

"Fluorescent" tubes tend to start a little delayed. There might occure a short flicker effect on start up. And it will take a short time till the fluorescent tube (or lamp) will shine in full 100% intensity. You can simulate this effect with a LED. Use a PWM enabled pin for the best effect.

FluorescentPin fluorescentLed {3}; // UNO PWM pins 3, 5, 6, 9, 10, 11

Heartbeat

A "heartbeat" LED will dim up and down permanently.

HeartbeatPin heartbeatLed {3}; // UNO PWM pins 3, 5, 6, 9, 10, 11

You can define thresholds for the minimum and maximum dim level.

.setInterval(10) will effect the speed of the dimming. Default value is 50.
.setMinBrightness(50) this will limit the lower end of the dimm range. Default value is 0 - meaning the LED will switch off.
.setMaxBrightness(240) this will limit the maximum brightness. Default value is 255. Highest value on an Arduino is 255.

Pulse (monoflop)


(click to see the effect)

A "pulse" is an high output for a (short) period of time which will return to low. It acts like a monoflop. A pulse turns on a LED for a defined period of time without using the delay() function. This means that other code can run at the same time without being interrupted by the LED code. The output acts like a monoflop.

PulsePin pulseLed {13}; // any output pin

You are not limited to LEDs. You can use this also to pulse a relay for a specific time. If your relay (or relay module) is LOW active, you can set the optional second parameter to indicate a LOW active output:

PulsePin pulseLed {13, LOW}; // if the pin should be LOW active, set second parameter

Rhythm

A "rhythm" LED can be set up to "blink" in a specific pattern. The rhythm LED supports 1 to 4 pairs of on/off times. This can be used for police cars, ambulances and similar vehicles. The default sequence is ECE2 (150, 60, 20, 270). But you can set any other sequence also (ECE1, HELLA 3, HELLA 4,...) . Just remember that you have to define the pattern in pairs of on and off times.

RhythmPin rhythmLed {13}; // declare LED and assign pin

To set the blink pattern/rhythm you have to hand over the on and off times in pairs. Up to 4 pairs (=8 values) are possible.

rhythmLed.setInterval(40, 40, 40, 40, 40, 40, 40, 220); // HELLA 4
rhythmLed.setInterval(25, 25, 25, 25, 25, 375);         // HELLA 3
rhythmLed.setInterval(150, 60, 20, 270);                // ECE 2 --> default
rhythmLed.setInterval(180, 320);                        // ECE 1 ON = 180ms, OFF = 320ms

Obviously, the variant with 180, 320 could be achieved as "BlinkLed" also.

Smooth

On PWM pins you can use a smooth dim up / down for a LED. When you switch the LED on, the LED will get brighter time by time. If you switch it off, it will slowly dimm down.

SmoothPin smoothLed {3}; // UNO PWM pins 3, 5, 6, 9, 10, 11

you can limit the maximum PWM value with following member function:

smoothLed.setMaxBrightness(240); // you can limit the maximum brightness. Highest value on Arduino is 255. Default 255.

The inverse function to retrieve the current brightness is:

uint16_t currentBrightness = smoothLed.getCurrentBrightness();

Effect

If you need a LED with several effects you can use EffectPin. It combines all described effects on a single output and you can change the effect during runtime.

Trafficlight

A traffic light consist of up to 3 LEDs (red, yellow, green) and can have several faces to be shown

states of a traffic light
0 OFF           // no LED is on
1 RED
2 REDYELLOW     // the RED and the Yellow are on
3 GREEN 
4 YELLOW 
5 YELLOWBLINK   // the traffic light is blinking yellow
6 GREENBLINK    // like used in Austria or Ukraine

Turn signal

The turn signals for a car consists of 2 side markers (for left and right) and an optional hazard warning light in the dashboard.

TurnsignalPin turnsignalPin{2, 3, 4}; // GPIO left, GPIO right, GPIO hazard warning light (optional)

You can switch the turn signal to LEFT, RIGHT and HAZARD. In case of HAZARD, the left and the right LED are blinking in sync. Additionally, the hazard LED for the dashboard indicates the status.

Neopixel WS2812

If you are running out of pins for your LEDs, you could use a strip with Neopixel / WS2812/ APA106 and add a lot of single effects. You can even mix discrete LEDs (connected to an Arduino PIN) and Neopixels in one sketch and run the same effect on different LED hardware. Obviously Neopixel can also be used with different colors. All classes are available with "Pixel":

AlternatingPixel
BlinkPixel
Bounce5Pixel
FlickerPixel
FluorescentPixel
HeartbeatPixel
OnOffPixel
PulsePixel
RhythmPixel
SmoothPixel
TrafficlightPixel
TurnsignalPixel

On hardware level the library relies on the "Adafruit Neopixel" library. Declare your strip handover the pixel you want to be effected:

#include <Noiasca_led.h>              // This library
#include <utility/Noiasca_neopixel.h> // the hardware interface for Neopixel

#include <Adafruit_NeoPixel.h>        // use the Adafruit library for Neopixel
constexpr uint16_t pixelCount = 32;   // the size of your strip
constexpr byte pixelPin = 8;          // the pin you have connected your Neopixel strip
Adafruit_NeoPixel strip(pixelCount, pixelPin, NEO_GRB + NEO_KHZ800);  // define your strip

BlinkPixel blinkPixelA(strip, 0);     // a blink LED on a Neopixel strip using pixel 0

The LED Driver HOLTEK HT16K33 (Version 0.3.0 upwards)

The HT16K33 is a LED driver for I2C. The LEDs can be arranged in a matrix with 8 common cathodes and 16 common anodes. A total of 128 LEDs can be driven by this IC.

All described effects can be used with the HT16K33. But keep in mind, that the HT16K33 has no PWM outputs. So only the simple effects (blink, pulse, bounce5, traffic lights,...) will work as intended.

The library contains a simple class for the HT16K33 driver. First you create an instance of the driver. When you create the effect LED, you hand over the driver object and a "pixel" which is one of the LED 0 to 127.

A minimal example for the HT16K33 looks like following:

#include <Wire.h>                     // I2C class for the port expander
#include <Noiasca_led.h>              // download from: https://werner.rothschopf.net/microcontroller/202202_tools_led_en.htm
#include <utility/Noiasca_HT16K33.h>  // needed to control HT16K33 - part of the LED tool kit

// create a expander object
HT16K33expander myHT16K33(0x70);      // create an expander instance at a specific I2C address (usually between 0x70 - 0x77)

// create your LED objects
// hand over the expander object and the number of LED (0..127)
BlinkHT16K33 blinkLEDA(myHT16K33, 0 + 0);        // a blink LED on a port expander  (first cathode, first Anode)

void setup() {
  Wire.begin();                        // needed for the HT16K33
  myHT16K33.begin();                   // start the HT16K33 object
  blinkLEDA.begin();                   // start the LED object
  blinkLEDA.setOnInterval(250);        // set the on time of a pin
}

void loop() {
  blinkLEDA.update();                  // call .update() for your object
}

The PWM Servo Driver PCA9685 (Version 0.1.0 upwards)

The PCA9685 is often used as PWM or Servo driver. The Noiasca Toolkit can be used to get all effects on the 16 outputs of the PCA9685. Just create a driver object ("pwm") with the Adafruit library and hand over this object and the pin number to an effect class with PCA9685.

AlternatingPCA9685
BlinkPCA9685
Bounce5PCA9685
FlickerPCA9685
FluorescentPCA9685
HeartbeatPCA9685
OnOffPCA9685
PulsePCA9685
RhythmPCA9685
SmoothPCA9685
TrafficlightPCA9685
TurnsignalPCA9685

On hardware level the library relies on the "Adafruit PWM Servo" library. Declare your PCA9685 device and handover the pin you want to be effected:

#include <Noiasca_led.h>                                 // the library with the LED effects
#include <utility/Noiasca_PCA9685.h>                     // needed for PWM Servo Driver
#include <Wire.h>                                        // I2C library for the PCA9685
#include <Adafruit_PWMServoDriver.h>                     // install with Library Manager
Adafruit_PWMServoDriver pwm = Adafruit_PWMServoDriver(); // create a pwm instance / a PCA9685 object
HeartbeatPCA9685 heartbeatLed {pwm, 1};                  // one pin on your PCA9685 object

The Portexpander PCF8574

The portexpander PCF8574 can be used for simple on/off effects like blink LED or to pulse a relay. Effects which need PWM don't work nicely with the PCF8574. I recommend to use another Portexpander

AlternatingPCF8574
BlinkPCF8574
Bounce5PCF8547
EffectPCF8547
FlickerPCF8547     // @note the PCF8547 is on/off only - no PWM. The effect will be limited.
FluorescentPCF8547 // @note the PCF8547 is on/off only - no PWM. The effect will be limited.
HeartbeatPCF8547   // @note the PCF8547 is on/off only - no PWM. The effect will be limited.
OnOffPCF8547
PulsePCF8547
RhythmPCF8547
SmoothPCF8547      // @note the PCF8547 is on/off only - no PWM. The effect will be limited.
TrafficlightPCF8547
TurnsignalPCF8547

Don't forget, the PCF8574 comes in two variants with addresses from either 0x20 - 0x27 or 0x38 - 0x3F.

Other functions (Buttons, Timer)

The Noiasca Toolkit contains classes to read easily buttons (momentary switches) and a simple timer to trigger events in your sketch. See the examples.

Links

(*) Disclosure: Some of the links above are affiliate links, meaning, at no additional cost to you I will earn a (little) comission if you click through and make a purchase. I only recommend products I own myself and I'm convinced they are useful for other makers.

History

First upload: 2022-02-02 | Version: 2024-03-22