XRAD'S issue with fade and blink switch functions LED

I have tried many different variations of fade and blink combos, and checked the variables and libraries, but the LEDs (basic LED with 200 ohm resitors) freeze funtion no matter what I have tried. I have looked at the library files and I do not know what I am doing wrong. Using HC-SR04 distance ultrasonic sensor for distance change and Teensy 4.0.

Either BLINK or FADE functions work fine by themselves. Any help appreciated!

ISSUE: if I try to switch from fade to blink or blink to fade, the LEDs do not switch funtions (or do not display the function correctly).

#include <LEDFader.h>
#include <Ultrasonic.h>

Ultrasonic ultrasonic(2, 20);
int distance;
unsigned long US_Distance_Ping_Timer = 0;


const int LED_RIGHT_EYE = 22;
const int LED_LEFT_EYE = 23;

int ledState = LOW;

unsigned long previousMillis = 0;

// constants won't change:
const long interval = 700;

#define LED_NUM 2

// 6 LEDs (perhaps 2 RGB LEDs)
LEDFader leds[LED_NUM] = {
  LEDFader(LED_RIGHT_EYE),
  LEDFader(LED_LEFT_EYE)
};

// millis variable used for many functions
//unsigned long currentMillis = 0;

//array of subjective milli run times
int MillisRunLengthTime[7] = { 20, 200, 800, 1000, 1500, 2000, 2500 };

//this is the key timer function, can use for MANY functions
boolean RunForThisAmountOfTime(unsigned long &startNowTimer, int runLengthTime) {
  unsigned long currentMillis = millis();
  if (currentMillis - startNowTimer >= runLengthTime) {
    startNowTimer = currentMillis;
    return true;
  } else return false;
}

void setup() {
  pinMode(LED_RIGHT_EYE, OUTPUT);
  pinMode(LED_LEFT_EYE, OUTPUT);
}

void loop() {
 if (RunForThisAmountOfTime(US_Distance_Ping_Timer, MillisRunLengthTime[1])) {
    distance = ultrasonic.read();
  }
  
if (distance <= 25) {
     BLINK();
  } 
   else if(distance > 25){
    FADER(); 
  }
}

void BLINK(){
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    previousMillis = currentMillis;
    if (ledState == LOW) {
      ledState = HIGH;
    } else {
      ledState = LOW;
    }
    digitalWrite(LED_RIGHT_EYE, ledState);
    digitalWrite(LED_LEFT_EYE, ledState);
  }
}


void FADER(){
  for (byte i = 0; i < LED_NUM; i++) {
    LEDFader *led = &leds[i];
    led->update();

    if (led->is_fading() == false) {
      if (led->get_value() == 0) {
        led->fade(255, 1000);
      }
      else {
        led->fade(0, 1000);
      }
    }
  }
}

So I cleaned up the code a bit...and tried other fade and blink functions, still no change in the original problem... Anyone with ideas?? Thanks!!

#include <LEDFader.h>
#include <Ultrasonic.h>

Ultrasonic ultrasonic(2, 20);
int distance;
unsigned long US_Distance_Ping_Timer = 0;

unsigned long LED_BLINK_Timer = 0;

const int LED_RIGHT_EYE = 4;
const int LED_LEFT_EYE = 3;

int ledState = LOW; 

#define LED_NUM 2

LEDFader leds[LED_NUM] = {
  LEDFader(LED_RIGHT_EYE),
  LEDFader(LED_LEFT_EYE)
};

 
unsigned long currentMillis = 0;

//array of subjective milli run times
int MillisRunLengthTime[7] = { 20, 200, 800, 1000, 1500, 2000, 2500 };

//this is the key timer function, can use for MANY functions
boolean RunForThisAmountOfTime(unsigned long &startNowTimer, int runLengthTime) {
  currentMillis = millis();
  if (currentMillis - startNowTimer >= runLengthTime) {
    startNowTimer = currentMillis;
    return true;
  } else return false;
}


void setup() {
  pinMode(LED_RIGHT_EYE, OUTPUT);
  pinMode(LED_LEFT_EYE, OUTPUT);
}

void loop() {

  if (RunForThisAmountOfTime(US_Distance_Ping_Timer, MillisRunLengthTime[1])) {
    distance = ultrasonic.read();
    Serial.print("Distance in CM: ");
    Serial.println(distance);
  }

  if (distance <= 25) {
    BLINK();
  } else {
    FADER();
  }
}

void BLINK() {
  if (RunForThisAmountOfTime(LED_BLINK_Timer, MillisRunLengthTime[3])) {
    if (ledState == LOW) {
      ledState = HIGH;
    } else {
      ledState = LOW;
    }
    digitalWrite(LED_RIGHT_EYE, ledState);
    digitalWrite(LED_LEFT_EYE, ledState);
  }
}


void FADER() {
  for (byte i = 0; i < LED_NUM; i++) {
    LEDFader *led = &leds[i];
      led->update();
    if (led->is_fading() == false) {
      if (led->get_value() == 0) {
        led->fade(255, 1000);
      } else {
        led->fade(0, 1000);
      }
    }
  }
}


Why do you have that odd function involved?

 if (RunForThisAmountOfTime(US_Distance_Ping_Timer, MillisRunLengthTime[1])) {
    distance = ultrasonic.read();
  }

Have you tried just getting what the sensor senses is the distance and printing that to the serial monitor, to see if it is making, um, sense?

Use without change or tweak an example. Leave the RunForThisAmountOfTime() out if the picture, don't even try to do the two functions based on distance. Yet.

a7

Here

When you are getting plausible data from the sensor, come back and say so. Post whatever you have that worked if it is not exactly the examlpe I linked.

a7

Thank you for reply. sensor works fine with the simple non blocking timer function, and in my larger code , that same function works fine with many motor functions. I have removed that function from the loop and replaced it with a very simple button switch. still same issue, neither the BLINK() nor the FADE() work together in the loop. Each works fine when the other is commented out.. I have tried many different non blocking fade and blink functions (other than the odd one above)...and still the same issue

 #include <LEDFader.h> 
 

unsigned long LED_BLINK_Timer = 0;
unsigned long LED_FADE_Timer = 0;
int value = 0;

int brightness = 0;   // how bright the LED is
int fadeAmount = 10;  // how many points to fade the LED by
unsigned long Fade_Timer = 0;

const int LED_RIGHT_EYE = 4;
const int LED_LEFT_EYE = 3;

int ledState = LOW;


#define LED_NUM 2

LEDFader leds[LED_NUM] = {
  LEDFader(LED_RIGHT_EYE),
  LEDFader(LED_LEFT_EYE)
};


unsigned long currentMillis = 0;

//array of subjective milli run times
int MillisRunLengthTime[7] = { 20, 200, 800, 1000, 1500, 2000, 2500 };

//this is the key timer function, can use for MANY functions
boolean RunForThisAmountOfTime(unsigned long &startNowTimer, int runLengthTime) {
  currentMillis = millis();
  if (currentMillis - startNowTimer >= runLengthTime) {
    startNowTimer = currentMillis;
    return true;
  } else return false;
}

const int buttonPin = 23;  
const int ledPin = 13;   
int buttonState = 0;   


void setup() {
 pinMode(ledPin, OUTPUT);
  pinMode(buttonPin, INPUT_PULLDOWN);
  pinMode(LED_RIGHT_EYE, OUTPUT);
  pinMode(LED_LEFT_EYE, OUTPUT);
}

void loop() { 
  buttonState = digitalRead(buttonPin);
  if (buttonState == HIGH) { 
    digitalWrite(ledPin, HIGH);
    BLINK();
  } else { 
    digitalWrite(ledPin, LOW);
   FADER();
  }
}
 

void BLINK() {
  if (RunForThisAmountOfTime(LED_BLINK_Timer, MillisRunLengthTime[3])) {
    if (ledState == LOW) {
      ledState = HIGH;
    } else {
      ledState = LOW;
    }
    digitalWrite(LED_RIGHT_EYE, ledState);
    digitalWrite(LED_LEFT_EYE, ledState);
  }
}


void FADER() {
  for (byte i = 0; i < LED_NUM; i++) {
    LEDFader *led = &leds[i];
    // led->update();
    if (led->is_fading() == false) {
      if (led->get_value() == 0) {
        led->fade(255, 1000);
      } else {
        led->fade(0, 1000);
      }
    }
    led->update();
  }
}

might be that the LEDs are stuck in last state change and not updated by next function....

I think you want to have both f/x running at the same time.

BLINK looks like it would be amenable to sharing.

FADE does not. I don't think.

You can write FADE to take a step each time it is called, rather than an entire breath or whatever you call it. Your other function is starved of attention, so it will not progress. It might even be derailed, as it would not be executing on the schedule it was designed for.

The idea is the same as BLINK, which only runs the code every so often no matter how you call it. Make your own loop variables and take a step each time FADE is called it does one step.

And any sense I make of RunForThisAmountOfTime() is that you have picked misleading name, or have been mislead by it or do not see how it absolves BLINK. You'd be better off just learning how millis() can work for you, and you would know exactly what the code was doing. Just sayin'.

a7

thank you for reply! AGREE..RunForThisAmountOfTime is a bad name...more like doThisWhenTimerExpires...

almost solved with this (still have a little timer bug):

#include <LEDFader.h>


unsigned long LED_BLINK_Timer = 0;
//unsigned long LED_FADE_Timer = 0;
int value = 0;

int brightness = 0;   // how bright the LED is
int fadeAmount = 10;  // how many points to fade the LED by
unsigned long Fade_Timer = 0;
unsigned long LED_FADE_Timer = 0;

const int LED_RIGHT_EYE = 4;
const int LED_LEFT_EYE = 3;

int ledState = LOW;


#define LED_NUM 2

LEDFader leds[LED_NUM] = {
  LEDFader(LED_RIGHT_EYE),
  LEDFader(LED_LEFT_EYE)
};


unsigned long currentMillis = 0;

//array of subjective milli run times
int MillisRunLengthTime[7] = { 20, 200, 800, 1000, 1500, 2000, 2500 };

//this is the key timer function, can use for MANY functions
boolean RunForThisAmountOfTime(unsigned long &startNowTimer, int runLengthTime) {
  currentMillis = millis();
  if (currentMillis - startNowTimer >= runLengthTime) {
    startNowTimer = currentMillis;
    return true;
  } else return false;
}

const int buttonPin = 23;
const int ledPin = 13;
int buttonState = 0;
 

void setup() {
  pinMode(ledPin, OUTPUT);
  pinMode(buttonPin, INPUT_PULLDOWN);
  pinMode(LED_RIGHT_EYE, OUTPUT);
  pinMode(LED_LEFT_EYE, OUTPUT);
}

void loop() {
  buttonState = digitalRead(buttonPin);
  if (buttonState == HIGH) {
    digitalWrite(ledPin, HIGH);
    BLINK();
  } else {
    digitalWrite(ledPin, LOW);
     FADENEW();
  }
}


void BLINK() {
  if (RunForThisAmountOfTime(LED_BLINK_Timer, MillisRunLengthTime[3])) {
    if (ledState == LOW) {
      ledState = HIGH;
      if(ledState == HIGH){
        brightness= 255;
      }
    } else {
      ledState = LOW;
      if (ledState == LOW){
        brightness = 0;
      }
    }
    //digitalWrite(LED_RIGHT_EYE, ledState);
    //digitalWrite(LED_LEFT_EYE, ledState);
    analogWrite(LED_RIGHT_EYE, brightness);
    analogWrite(LED_LEFT_EYE, brightness);
  }
}

void FADENEW(){
 if (RunForThisAmountOfTime(LED_FADE_Timer, MillisRunLengthTime[0])) {
    analogWrite(LED_RIGHT_EYE, brightness);
    analogWrite(LED_LEFT_EYE, brightness);
    brightness = brightness + fadeAmount;
    if (brightness <= 0 || brightness >= 255) {
      fadeAmount = -fadeAmount;
    }
  }
}


void FADER() {
  for (byte i = 0; i < LED_NUM; i++) {
    LEDFader *led = &leds[i];
    // led->update();
    if (led->is_fading() == false) {
      if (led->get_value() == 0) {
        led->fade(255, 1000);
      } else {
        led->fade(0, 1000);
      }
    }
    led->update();
  }
}

here is a cleaned up code for anyone wanting to fade or blink LEDs for arduino projects....I am sure there are better ways of doing this, but this works...
also: 'RunForThisAmountOfTime' is better as 'RunTIMERForThisAmountOfTime'

unsigned long CLEAR_LED_Timer = 0;
unsigned long LED_BLINK_Timer = 0;
unsigned long LED_FADE_Timer = 0;

int value = 0;
int brightness = 0;
int fadeAmount = 5;

const int LED_RIGHT_EYE = 4;
const int LED_LEFT_EYE = 3;

int ledState = LOW;
bool eyeStateClear = true;

unsigned long currentMillis = 0;

//array of subjective milli run times
int MillisRunLengthTime[8] = { 20, 100, 200, 800, 1000, 1500, 2000, 2500 };

//this is the key timer function, can use for MANY functions
boolean RunForThisAmountOfTime(unsigned long &startNowTimer, int runLengthTime) {
  currentMillis = millis();
  if (currentMillis - startNowTimer >= runLengthTime) {
    startNowTimer = currentMillis;
    return true;
  } else return false;
}

const int buttonPin = 23;
const int ledPin = 13;
int buttonState = 0;

enum eyeStates {
  BLINK_BOTH_EYES,  // blink both eyes
  FADE_BOTH_EYES,   // fade both eyes
  CLEAR_EYES,       // clear eye variables
  BLINK_RIGHT_EYE,  //
  BLINK_LEFT_EYE,
  BOTH_EYES_ON,
  BOTH_EYES_OFF
};

enum eyeStates EYE_FUNCTIONS();


void setup() {
  pinMode(ledPin, OUTPUT);
  pinMode(buttonPin, INPUT_PULLDOWN);
  pinMode(LED_RIGHT_EYE, OUTPUT);
  pinMode(LED_LEFT_EYE, OUTPUT);
}



void loop() {
  buttonState = digitalRead(buttonPin);
  if (buttonState == HIGH) {
    //digitalWrite(ledPin, HIGH);
    eyeStateClear = true;
    EYE_FUNCTIONS(BLINK_BOTH_EYES);
  } else {
    //digitalWrite(ledPin, LOW);
    if (eyeStateClear == true) {
      eyeStateClear = false;
      EYE_FUNCTIONS(CLEAR_EYES);
    }
    EYE_FUNCTIONS(FADE_BOTH_EYES);
  }
}


void EYE_FUNCTIONS(int var) {
  switch (var) {
    case 0:  //blink LEDs
      if (RunForThisAmountOfTime(LED_BLINK_Timer, MillisRunLengthTime[2])) {
        if (ledState == LOW) {
          ledState = HIGH;
          if (ledState == HIGH) {
            brightness = 255;
          }
        } else {
          ledState = LOW;
          if (ledState == LOW) {
            brightness = 0;
          }
        }
        analogWrite(LED_RIGHT_EYE, brightness);
        analogWrite(LED_LEFT_EYE, brightness);
      }
      break;
    case 1:  //fade LEDs
      if (RunForThisAmountOfTime(LED_FADE_Timer, MillisRunLengthTime[0])) {
        brightness = brightness + fadeAmount;
        if (brightness <= 0 || brightness >= 255) {
          fadeAmount = -fadeAmount;
        }
      }
      analogWrite(LED_RIGHT_EYE, brightness);
      analogWrite(LED_LEFT_EYE, brightness);
      break;

    case 2:  //clear LEDs
      fadeAmount = 0;
      brightness = 0;
      LED_FADE_Timer = 0; 
      analogWrite(LED_RIGHT_EYE, 0);
      analogWrite(LED_LEFT_EYE, 0);
      fadeAmount = 5;
      break;

    case 3:  //blink RIGHT eye
      if (RunForThisAmountOfTime(LED_BLINK_Timer, MillisRunLengthTime[2])) {
        if (ledState == LOW) {
          ledState = HIGH;
          if (ledState == HIGH) {
            brightness = 255;
          }
        } else {
          ledState = LOW;
          if (ledState == LOW) {
            brightness = 0;
          }
        }
        analogWrite(LED_RIGHT_EYE, brightness);
        analogWrite(LED_LEFT_EYE, 0);
      }
      break;

    case 4:  //blink LEFT eye
      if (RunForThisAmountOfTime(LED_BLINK_Timer, MillisRunLengthTime[1])) {
        if (ledState == LOW) {
          ledState = HIGH;
          if (ledState == HIGH) {
            brightness = 255;
          }
        } else {
          ledState = LOW;
          if (ledState == LOW) {
            brightness = 0;
          }
        }
        analogWrite(LED_RIGHT_EYE, 0);
        analogWrite(LED_LEFT_EYE, brightness);
      }
      break;

    case 5:  //both eyes ON
      analogWrite(LED_RIGHT_EYE, 255);
      analogWrite(LED_LEFT_EYE, 255);
      break;

    case 6:  //both eyes OFF
      analogWrite(LED_RIGHT_EYE, 0);
      analogWrite(LED_LEFT_EYE, 0);
      break;
  }
}

 

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.