Page 1 of 1
Forum

Welcome to the Tweaking4All community forums!
When participating, please keep the Forum Rules in mind!

Topics for particular software or systems: Start your topic link with the name of the application or system.
For example “MacOS X – Your question“, or “MS Word – Your Tip or Trick“.

Please note that switching to another language when reading a post will not bring you to the same post, in Dutch, as there is no translation for that post!




LED effects - Fade ...
 
Share:
Notifications
Clear all

[Solved] LED effects - Fade out on rainbow cycle

5 Posts
3 Users
2 Likes
3,679 Views
(@arnaud)
Active Member
Joined: 3 years ago
Posts: 5
Topic starter  

Hello,

As I explained it I would like to add a fade out a the end of the rainbow cycle effect to have a transition between rainbow and meteor rain.

I tested with a FastLED.setBrightness() and with a strip.setBrightness(), unfortunately in the both cases the led strip freezes.

I tried the code hereafter, it works to fade in not to fade out.
In fade out version, all the led decrease to become black but just after the led light up again and the color of each led seems to change randomly but gradually. 

//fadeInRainbow
void fadeInRainbow(int SpeedDelay) {

  byte *c;
  uint16_t i, j;
  for(j = 0; j < 256; j=j+1) {
    for(i=0; i< NUM_LEDS; i++) {
      c=Wheel((i * 256 / NUM_LEDS) & 255);
      setPixel(i, *c*(j/256.0), *(c+1)*(j/256.0), *(c+2)*(j/256.0));
    }
 
    showStrip();
    delay(SpeedDelay);
  }
}

//fadeOutRainbow
//WORK IN  PROGRESS
void fadeOutRainbow(int SpeedDelay) {

  byte *c;
  uint16_t i, j;
  for(j = 255; j >= 0; j=j-2) {
    for(i=0; i< NUM_LEDS; i++) {
      c=Wheel((i * 256 / NUM_LEDS) & 255);
      setPixel(i, *c*(j/256.0), *(c+1)*(j/256.0), *(c+2)*(j/256.0));
    }
 
    showStrip();
    delay(SpeedDelay);
  }
}

 

The best transition I found is to remove the reset of the LED strip at the beginning of the meteor rain code. Remove of setAll(0,0,0)
But it's not a fade out.

 

Unfortunately I forgot to film the version of the code above.

https://youtu.be/vKkichWFwK8


   
ReplyQuote
 Hans
(@hans)
Famed Member Admin
Joined: 11 years ago
Posts: 2660
 

Thanks Arnaud for taking the time and effort to post this in the forum - it is much appreciated 😊 

Thanks for the very cool video! I like what you've done! 👍 
Would you mind sharing the full code once we have it all working?

I think I may have misunderstood your earlier question, so let's try again ...

We probably should consider using the fadeToBlack function.
You can use the function of my project, or the FastLED build-in function.
(I prefer the FastLED library, so if you're going that route, we can eventually cleanup the code and remove the code for NeoPixel)

So this could look something like this:

void fadeOutRainbow(int SpeedDelay) {

// 20 times reduce the color brightness by 25%, reaching close to zero (black)
for(int j=1; j<20; j++) {
   for(int i=0; i< NUM_LEDS; i++) {
     fadeToBlack(i, 64);
    }
 
    showStrip();
    delay(SpeedDelay);
  }
}

Now I haven't tested this code, and there are 2 point to pay attention to;

In the for-j loop, I've used the random value of 20.

In the for-i loop I do a fadeToBlack for all LEDs by 64, which translates to a 64/256 = 25% brightness reduction.
So in each step, the current led value will be reduced by 25%.

So 20 times a 25% reduction, should get a 255 value all the way down to about 1 (which is pretty much "off").
If you really want to absolutely go to zero then you''l need up to 38 steps.
(I didn't use any super genius math for that - I just made a little excel sheet where each row reduces the previous row by 25%)

Note that an x% reduction per step eventually will reach zero, no matter what the starting value/color was. It will never go below zero though.

You'll have to experiment a little to see what values work best for your setup.


   
ReplyQuote
(@arnaud)
Active Member
Joined: 3 years ago
Posts: 5
Topic starter  

Hi Hans,

Thank you very much, it's exactly what I need and your explanations are very clear.
I replaced 20 times by 53 times and 64 by 26 to have 10% and a slower fade to black. Like you I used a spreadsheet.

Hereafter there is the working code.
Inside there are the fire effect and the theater effect that I keep to use after on a 200 LED strip.

// Code source: Hans Luijten
// Website: https://www.tweaking4all.com

#include <Adafruit_NeoPixel.h>
#include <EEPROM.h>
//#include <FastLED.h> *Not used for the moment

#define NUM_LEDS 100
#define PIN 6
Adafruit_NeoPixel strip = Adafruit_NeoPixel(NUM_LEDS, PIN, NEO_GRB + NEO_KHZ800);


void setup()
{
strip.begin();
strip.show(); // Initialize all pixels to 'off'
}

// REPLACE FROM HERE
void loop() {

int i;
int j;
int k;

{
fadeInRainbow(5);
}

for(i=0; i<random (5,15); i++) {
rainbowCycleWithSparkle(50,20);
}

{
fadeOutRainbow(20);
}

for(j=0; j<random (0,4); j++) {
meteorRain(0xff,0xff,0xff,10, 64, true, 30);
}

{
meteorRainTransition(0xff,0xff,0xff,10, 64, true, 30);
}

{
colorWipeReversed(0xff,0xff,0xff, 10);
// colorWipeReversed(0x00,0x00,0x00, 20);
}

for(k=0; k<random (3000,20000); k++) {
Sparkle(0xff, 0xff, 0xff, 0);
}

}


// *************************
// ** LEDEffect Functions **
// *************************


//fadeInRainbow
void fadeInRainbow(int SpeedDelay) {

byte *c;
uint16_t i, j;
for(j = 0; j < 256; j=j+1) {
for(i=0; i< NUM_LEDS; i++) {
c=Wheel((i * 256 / NUM_LEDS) & 255);
setPixel(i, *c*(j/256.0), *(c+1)*(j/256.0), *(c+2)*(j/256.0));
}

showStrip();
delay(SpeedDelay);
}
}

//Sparkle
void Sparkle(byte red, byte green, byte blue, int SpeedDelay) {
int Pixel = random(NUM_LEDS);
setPixel(Pixel,red,green,blue);
showStrip();
delay(SpeedDelay);
setPixel(Pixel,0,0,0);
}

//colorWipeReversed
void colorWipeReversed(byte red, byte green, byte blue, int SpeedDelay) {
for(uint16_t i=NUM_LEDS; i>0; i--) {
setPixel(i, red, green, blue);
showStrip();
delay(SpeedDelay);
}
}

//RainbowCycleWithSparkle
void rainbowCycleWithSparkle(int SparkleDelay, int SpeedDelay) {
byte *c;
uint16_t i, j;

for(j=0; j<256; j++) {
for(i=0; i< NUM_LEDS; i++) {
c=Wheel(((i * 256 / NUM_LEDS) + j) & 255);
setPixel(i, *c, *(c+1), *(c+2));
}
showStrip();
delay(SpeedDelay);
int Pixel = random(NUM_LEDS);
setPixel(Pixel,0xff,0xff,0xff);
showStrip();
delay(SparkleDelay);
}
}

// used by rainbowCycleWithSparkle
byte * Wheel(byte WheelPos) {
static byte c[3];

if(WheelPos < 85) {
c[0]=WheelPos * 3;
c[1]=255 - WheelPos * 3;
c[2]=0;
} else if(WheelPos < 170) {
WheelPos -= 85;
c[0]=255 - WheelPos * 3;
c[1]=0;
c[2]=WheelPos * 3;
} else {
WheelPos -= 170;
c[0]=0;
c[1]=WheelPos * 3;
c[2]=255 - WheelPos * 3;
}

return c;
}

//fadeOutRainbow
void fadeOutRainbow(int SpeedDelay) {

// 53 times reduce the color brightness by 10%, reaching close to zero (black)
for(int j=1; j<53; j++) {
for(int i=0; i< NUM_LEDS; i++) {
fadeToBlack(i, 26); // 26 / 256 = 10% brightness reduction
}

showStrip();
delay(SpeedDelay);
}
}

//theaterChaseRainbow
// not used for the moment
void theaterChaseRainbow(int SpeedDelay) {
byte *c;

for (int j=0; j < 256; j++) { // cycle all 256 colors in the wheel
for (int q=0; q < 3; q++) {
for (int i=0; i < NUM_LEDS; i=i+3) {
c = Wheel( (i+j) % 255);
setPixel(i+q, *c, *(c+1), *(c+2)); //turn every third pixel on
}
showStrip();

delay(SpeedDelay);

for (int i=0; i < NUM_LEDS; i=i+3) {
setPixel(i+q, 0,0,0); //turn every third pixel off
}
}
}
}

//Fire
// not used for the moment
void Fire(int Cooling, int Sparking, int SpeedDelay) {
static byte heat[NUM_LEDS];
int cooldown;

// Step 1. Cool down every cell a little
for( int i = 0; i < NUM_LEDS; i++) {
cooldown = random(0, ((Cooling * 10) / NUM_LEDS) + 2);

if(cooldown>heat[i]) {
heat[i]=0;
} else {
heat[i]=heat[i]-cooldown;
}
}

// Step 2. Heat from each cell drifts 'up' and diffuses a little
for( int k= NUM_LEDS - 1; k >= 2; k--) {
heat[k] = (heat[k - 1] + heat[k - 2] + heat[k - 2]) / 3;
}

// Step 3. Randomly ignite new 'sparks' near the bottom
if( random(255) < Sparking ) {
int y = random(7);
heat[y] = heat[y] + random(160,255);
//heat[y] = random(160,255);
}

// Step 4. Convert heat to LED colors
for( int j = 0; j < NUM_LEDS; j++) {
setPixelHeatColor(j, heat[j] );
}

showStrip();
delay(SpeedDelay);
}

// used by Fire
void setPixelHeatColor (int Pixel, byte temperature) {
// Scale 'heat' down from 0-255 to 0-191
byte t192 = round((temperature/255.0)*191);

// calculate ramp up from
byte heatramp = t192 & 0x3F; // 0..63
heatramp <<= 2; // scale up to 0..252

// figure out which third of the spectrum we're in:
if( t192 > 0x80) { // hottest
setPixel(Pixel, 255, 255, heatramp);
} else if( t192 > 0x40 ) { // middle
setPixel(Pixel, 255, heatramp, 0);
} else { // coolest
setPixel(Pixel, heatramp, 0, 0);
}
}

//meteorRain
void meteorRain(byte red, byte green, byte blue, byte meteorSize, byte meteorTrailDecay, boolean meteorRandomDecay, int SpeedDelay) {
//setAll(0,0,0);

for(int i = 0; i < NUM_LEDS+NUM_LEDS; i++) {


// fade brightness all LEDs one step
for(int j=0; j<NUM_LEDS; j++) {
if( (!meteorRandomDecay) || (random(10)>5) ) {
fadeToBlack(j, meteorTrailDecay );
}
}

// draw meteor
for(int j = 0; j < meteorSize; j++) {
if( ( i-j <NUM_LEDS) && (i-j>=0) ) {
setPixel(i-j, red, green, blue);
}
}

showStrip();
delay(SpeedDelay);
}
}

//meteorRainTransition
void meteorRainTransition(byte red, byte green, byte blue, byte meteorSize, byte meteorTrailDecay, boolean meteorRandomDecay, int SpeedDelay) {
setAll(0,0,0);

// old:
// for(int i = 0; i < NUM_LEDS+NUM_LEDS; i++) {

// new:
for(int i = 0; i < NUM_LEDS; i++) {

// fade brightness all LEDs one step
for(int j=0; j<NUM_LEDS; j++) {
if( (!meteorRandomDecay) || (random(10)>5) ) {
fadeToBlack(j, meteorTrailDecay );
}
}

// draw meteor
for(int j = 0; j < meteorSize; j++) {
if( ( i-j <NUM_LEDS) && (i-j>=0) ) {
setPixel(i-j, red, green, blue);
}
}

showStrip();
delay(SpeedDelay);
}
}

// used by meteorRain
void fadeToBlack(int ledNo, byte fadeValue) {
#ifdef ADAFRUIT_NEOPIXEL_H
// NeoPixel
uint32_t oldColor;
uint8_t r, g, b;
int value;

oldColor = strip.getPixelColor(ledNo);
r = (oldColor & 0x00ff0000UL) >> 16;
g = (oldColor & 0x0000ff00UL) >> 8;
b = (oldColor & 0x000000ffUL);

r=(r<=10)? 0 : (int) r-(r*fadeValue/256);
g=(g<=10)? 0 : (int) g-(g*fadeValue/256);
b=(b<=10)? 0 : (int) b-(b*fadeValue/256);

strip.setPixelColor(ledNo, r,g,b);
#endif
#ifndef ADAFRUIT_NEOPIXEL_H
// FastLED
leds[ledNo].fadeToBlackBy( fadeValue );
#endif
}


// REPLACE TO HERE




// ***************************************
// ** FastLed/NeoPixel Common Functions **
// ***************************************

// Apply LED color changes
void showStrip() {
#ifdef ADAFRUIT_NEOPIXEL_H
// NeoPixel
strip.show();
#endif
#ifndef ADAFRUIT_NEOPIXEL_H
// FastLED
FastLED.show();
#endif
}

// Set a LED color (not yet visible)
void setPixel(int Pixel, byte red, byte green, byte blue) {
#ifdef ADAFRUIT_NEOPIXEL_H
// NeoPixel
strip.setPixelColor(Pixel, strip.Color(red, green, blue));
#endif
#ifndef ADAFRUIT_NEOPIXEL_H
// FastLED
leds[Pixel].r = red;
leds[Pixel].g = green;
leds[Pixel].b = blue;
#endif
}

// Set all LEDs to a given color and apply it (visible)
void setAll(byte red, byte green, byte blue) {
for(int i = 0; i < NUM_LEDS; i++ ) {
setPixel(i, red, green, blue);
}
showStrip();
}

   
Hans reacted
ReplyQuote
 Hans
(@hans)
Famed Member Admin
Joined: 11 years ago
Posts: 2660
 

Hi Arnaud!

Awesome! Glad to hear this did the trick and thank you for posting the full code! 😊

 


   
ReplyQuote
(@Anonymous)
Joined: 1 second ago
Posts: 0
 

Many many THANKS! for sharing this Sketch!!!! Now i have my RainbowSparkle Code ♥


   
Hans reacted
ReplyQuote


Like what you see and you'd like to help out? 

The best way to help is of course by assisting others with their questions here in the forum, but you can also help us out in other ways:

- Do your shopping at Amazon, it will not cost you anything extra but may generate a small commission for us,
- send a cup of coffee through PayPal ($5, $10, $20, or custom amount),
- become a Patreon,
- donate BitCoin (BTC), or BitCoinCash (BCH).

Share: