0

I'm trying to call a class function that pulses an LED "x" number of times. I dont want to use a delay, which is making it tough. If I use a while loop, the LED just stays on. I attach an interrupt in the begin() - the location of the LED is pin 13

I call the following in my sketch like so:

robot.lights.pulse(0, 2000, 10000, 500); //in milliseconds

My goal is to pulse an LED "x" number of time at a rate I specify.

This is the code inside my class:

void StatusLights::begin(int locations[]){
    for(int i=0;i<NUM_OF_LIGHTS;i++){
        this->locations[i]=locations[i];
        pinMode(locations[i], OUTPUT);
    }

    ledState = LOW;
    previousMillis = 0;
    attachInterrupt(0, pulse_ISR, RISING);

};

void StatusLights::pulse(int location, int interval, int count, int speed){

    int value = 0;
    previousMillis = 0;
    // while(pulsecnt<count) {
        long currentMillis = millis();

        if (currentMillis - previousMillis >= interval) {
            previousMillis = currentMillis;
            value = 128+127*cos(2*PI/interval*(speed-currentMillis));
            analogWrite(locations[location], value); 
        };
    // };
    // digitalWrite(locations[location], LOW);
};

void pulse_ISR() {
    pulsecnt++;
};

This is my first time using interrupts to do this - I'm really trying to avoid delays since i need other things to happen synchronously.

Thanks!

  • Can you show us a working sketch? The currentMillis should be unsigned long. What kind of pulse do you want, because the human eye has a log scale and you use cosine. How often do you want an update of the led brightness? – Jot Jan 19 at 15:20
  • @Jot added a function call to my question. thanks – rcpilotp51 Jan 19 at 17:12
  • A working sketch is something we can try without guessing what the rest of the code is. I would like to see the rest of the sketch because I think you have made it too complex. Start with the 'update' function to keep it going as @JRobert writes in his answer. That is a common way to deal with it in arduino projects. – Jot Jan 19 at 18:35
  • then no i dont without the other five classes – rcpilotp51 Jan 19 at 20:53
  • Is your previousMillis a long as well? That's not okay. This is what I mean with guessing. – Jot Jan 19 at 21:17
1

You'll want a class function that decides whether 'now' is time to toggle the LED or not, and returns quickly. Call that function frequently from your loop function. Your other class functions will set or clear the whether the LED is to toggled, and when, how many times, etc. Something like the following pseudo-code, which is not a full solution but should point out the essential details:

void loop()
{
   myStatusLights.updateLED();     // call this frequently
}

...

void StatusLights::updateLED(){
  if LED_active,
     if it's time to change the LED,
        toggle LED on/off;
        if LED has toggled enough times,
           set LED_active false;
        endif;
     endif;
  endif;
}

Update:

How would you refresh the count, track the pulses, and refresh the state of the status light without any parameters?

Some class-function must initiate the blinking, whether it knows to do it itself or it is called from your application code. That class-function will need to set those parameters. If it to be called from outside, perhaps the outside sets them - ? Only you know that. Either way, they will need to get saved in the class' private data so the .updateLED() function can have access to them. The .updateLED() function will, for instance, count down the remaining number blinks to display, keep track of whether the LED is on or off, actually turn it on or off, etc., until there is nothing left for it to do. In that case it just quickly returns without doing anything.

  • I'm not sure I follow toggle LED on/off; if LED has toggled enough times, set LED_active false; endif; this is exactly what im trying to do, but I'm not sure of the syntax - sorry the sudo code isn't helping in this case. @JRobert – rcpilotp51 Jan 19 at 17:07
  • I understand that you want to repeatedly call an update function - How would you refresh the count, track the pulses, and refresh the state of the status light without any parameters? what if i want to set pulse the led 10 times in the setup function? – rcpilotp51 Jan 19 at 17:11
  • @rcpilotp51, you have a class for status lights and you don't know where to hold the status of lights? cplusplus.com/doc/tutorial/classes – Juraj Jan 19 at 18:01
  • @Juraj i actually have an array of light locations "pins" and want to call them based on other events and want them to do different things...do i need an update function for each? – rcpilotp51 Jan 19 at 20:58
  • You don't need a function for each; one update function can loop through the array of LEDs and apply the same logic to each one, based on each particular LED's class variables' values. Each LED will needs its own set of e.g., pin#, blink-interval, blinks-remaining, etc. – JRobert Jan 21 at 17:30

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.