looping an if statement

I already asked this question yesterday but didn't get an answer, today i simplified the code a lot and added more clear explanation.

Here's the code:

int pin_switch = 2;
int pin_LED = 3;
int pin_LED2 = 4;

boolean oldSwitchState = LOW;
boolean newSwitchState = LOW;
boolean LEDstatus = LOW;
boolean LED2status = LOW;

unsigned long previousMillis = 0;
const long period = 3000;
 
void setup()
{
    Serial.begin(9600);
    pinMode(pin_switch, INPUT);
    pinMode(pin_LED, OUTPUT);
    pinMode(pin_LED2, OUTPUT);
    digitalWrite(pin_LED,LOW);
}
 
void loop()
{
    newSwitchState = digitalRead(pin_switch);
 
    if (millis() - previousMillis >= period) {
      digitalWrite(pin_LED2, LOW);
      LED2status = LOW;
    }
    else if ( LED2status == LOW ){
      digitalWrite(pin_LED2, HIGH);
      LED2status = HIGH;
    }
    if ( newSwitchState != oldSwitchState ){
       if ( newSwitchState == HIGH ){
       previousMillis = millis();
      if ( LEDstatus == LOW ){
        digitalWrite(pin_LED, HIGH);
        LEDstatus = HIGH;
        Serial.println("ON");
      }
      else{
        digitalWrite(pin_LED, LOW);
        LEDstatus = LOW;
        Serial.println("OFF");
      }
       }
       oldSwitchState = newSwitchState;
    }
}

What is this code doing?

Each time push button pressed it turn on LED1 and LED2 and start counting, after (const long period) seconds turn off LED2. pressing the push button again will turn off LED1 and turn on LED2 and starts counting again.

What i want this code to do?

I want to keep checking the if statement; if LEDstatus == LOW do that. check again; is it still == LOW? do that again (in a loop).

What is the problem?

(If LEDstatus == LOW) doing the "commands" inside that IF only once.

PS. i don't want to use while loop.

I want to keep checking the if statement; if LEDstatus == LOW do that. check again; is it still == LOW? do that again (in a loop).

The if statement does NOT loop. If you want to check the statement over and over, you have to do the checking in the body of some statement that does loop. Like the aptly-named loop() function.

PaulS:
The if statement does NOT loop. If you want to check the statement over and over, you have to do the checking in the body of some statement that does loop. Like the aptly-named loop() function.

i'm not familiar with aptly-named loop(), can you please provide an example?

J35U51510V3:
i'm not familiar with aptly-named loop(), can you please provide an example?

You're kidding, right?

You mean:
aptly-named loop.PNG

aptly-named loop.PNG

There are 2 functions that must be included in an Arduino sketch. The setup() function runs 1 time and is used to initailize the machine. The other is the loop() function that runs over and over (loops) endlessly and contains the body of the program.

PaulS:
You're kidding, right?

PaulS:
you have to do the checking in the body of some statement that does loop.

i mean how i do what you said inside the loop, English is my third language please bear with me...

i mean how i do what you said inside the loop,

void loop()
{
   // some stuff


   if(LEDStatus == LOW)
   {
       // Do whatever you want to do...
   }

   // more stuff
}

The loop() function is called in a loop, so LEDStatus will be compared to LOW every time loop() is called.

PaulS:

void loop()

{
  // some stuff

if(LEDStatus == LOW)
  {
      // Do whatever you want to do...
  }

// more stuff
}




The loop() function is called in a loop, so LEDStatus will be compared to LOW every time loop() is called.

yes but i can't have the toggle thing if i just remove the other parts of that code in my first post!

but i can't have the toggle thing if i just remove the other parts of that code in my first post!

The "other parts" of your code go where the comment says "some stuff" or where the comment says "more stuff", depending on whether you want the "other parts" to happen before, or after, you check the value in LEDStatus.

PaulS:
The "other parts" of your code go where the comment says "some stuff" or where the comment says "more stuff", depending on whether you want the "other parts" to happen before, or after, you check the value in LEDStatus.

like this: ?

void loop()
{
   newSwitchState = digitalRead(pin_switch);

   if (millis() - previousMillis >= period) {
     digitalWrite(pin_LED2, LOW);
     LED2status = LOW;
   }
   else if ( LED2status == LOW ){
     digitalWrite(pin_LED2, HIGH);
     LED2status = HIGH;
   }
   if ( newSwitchState != oldSwitchState ){
      if ( newSwitchState == HIGH ){
      previousMillis = millis();
      }
      oldSwitchState = newSwitchState;
   }
   if ( LEDstatus == LOW ){
     digitalWrite(pin_LED, HIGH);
     LEDstatus = HIGH;
     Serial.println("ON");
   }
   else{
     digitalWrite(pin_LED, LOW);
     LEDstatus = LOW;
     Serial.println("OFF");
   }
}

but now the LED1 turns on off so quick and i can't toggle it!

Instead of telling how you think you should write the code, tell us what you are trying to do.

PaulS:
Instead of telling how you think you should write the code, tell us what you are trying to do.

i'm sorry but i clearly said what i want in the first post, there's nothing else i didn't mentioned there!

There are some things missing from your description:

  • You end in a different state then you start. So how to continue? Is led1 supposed to turn on ever again?
  • What should happen when you press the button again when led2 is on?

And about the if(), I really don't see the problem.

  • You do have a non-blocking loop called loop()
  • You have a statement you want to check and you do know how
  • You want to check that over and over again
  • Aka, just make it part of that damn loop() :smiley:

And a tip about keeping track of output states:

    digitalWrite(pin_LED2, LOW);
     LED2status = LOW;

There will be a moment you forget to update that status variable as well. And hé, who want to do stuff twice anyway?
Solution 1
Don't call the digitalWrite() there. Only set the state variable where you want to change (or define) the state of the output. And just unconditionally call digitalWrite() with that state in the loop()

void loop(){
  if(youWantToChangeState){
    state = HIGH;
  }
  //more stuff
  //..even more stuff
  
  digitalWrite(pin, state);
}

Solution 2
In my opinion he easiest solution. Don't bother with the state variable at all. Just use digitalRead() instead. Yes, this also works on an output :slight_smile: