Make a mini menu with a button and two leds

Hey
I have 3 LEDs and 2 buttons, 2 of the LEDs are indicator of what state the third LED should eighter blink or fade when startSwitch is pressed, that is chosen by the second button(selectionSwitch).
I do not get it right when I switch the states program1Flag and program2Flag. Can some one guide me what I am missing?
Thanks!


unsigned long startMillis;
unsigned long periodStartMillis;
unsigned long currentMillis;
unsigned long startMillis1;
unsigned long periodStartMillis1;
unsigned long currentMillis1;
unsigned long blinkStartMillis;
unsigned long fadeStartMillis;
unsigned long debounceStartMillis;
unsigned long debounceStartMillis1;
unsigned long debouncePeriod = 20;
const unsigned long period = 50;  //checking button every 50ms
const byte startSwitch = 2;
const byte selectionSwitch = 3;
byte currentButtonState;
byte previousButtonState;
byte currentButtonState1;
byte previousButtonState1;
const unsigned long blinkPeriod = 1000;  //blink period
const unsigned long fadePeriod = 10;  //fade period
const byte led = 10;

const byte program1LED = 6;
const byte program2LED = 5;
byte brightness = 0;  //initial brightness of LED
byte increment = 1;  //amount to change PWM value at each change
bool actionFlag = false;
bool program1Flag = true;
bool program2Flag = false;
boolean debouncing = false;



int lastButtonState = LOW;
int lastButtonState1 = LOW;

unsigned long lastDebounceTime = 0;// the last time the output pin was toggled
unsigned long debounceDelay = 50;
unsigned long lastDebounceTime1 = 0;// the last time the output pin was toggled
unsigned long debounceDelay1 = 50;


void setup()
{
  Serial.begin(115200);
  pinMode(startSwitch, INPUT_PULLUP);
  pinMode(selectionSwitch, INPUT_PULLUP);
  pinMode(led, OUTPUT);
  blinkStartMillis = millis();  //start time of blinking LED
  fadeStartMillis = millis();  //start time of fading LED
  periodStartMillis = millis();
  startMillis = millis();
  program1Flag = true;
  digitalWrite(program1LED, HIGH);
}

void loop()
{
  currentMillis = millis();
  int reading = digitalRead(startSwitch);
  int reading1 = digitalRead(selectionSwitch);


  

  // SELECTIONSWITCH


  if (reading1 != lastButtonState1) {
    // reset the debouncing timer
    lastDebounceTime1 = millis();
  }

  if ((millis() - lastDebounceTime1) > debounceDelay1) {
    // whatever the reading is at, it's been there for longer than the debounce
    // delay, so take it as the actual current state:

    // if the button state has changed:
    if (reading1 != currentButtonState1) {
      currentButtonState1 = reading1;

      // only toggle the LED if the new button state is pressed
      if (currentButtonState1 == LOW and program1Flag == true) {
        
        program1Flag = false;
        program2Flag = true;
        digitalWrite(program1LED, LOW);
        digitalWrite(program2LED, HIGH);
      }
      if (currentButtonState1 == LOW and program2Flag == true) {
        
        program1Flag = true;
        program2Flag = false;
        digitalWrite(program1LED, HIGH);
        digitalWrite(program2LED, LOW);
      }
    }
  }


  // startSwitch
if (reading != lastButtonState) {
    // reset the debouncing timer
    lastDebounceTime = millis();
  }

  if ((millis() - lastDebounceTime) > debounceDelay) {
    // whatever the reading is at, it's been there for longer than the debounce
    // delay, so take it as the actual current state:

    // if the button state has changed:
    if (reading != currentButtonState) {
      currentButtonState = reading;

      // only toggle the LED if the new button state is HIGH
      if (currentButtonState == LOW) {
        actionFlag = !actionFlag;
      }
    }
  }
  if (actionFlag == true && program1Flag == true) //take actions based on the state of the action flag
  {
    blink();

  }
  if (actionFlag == true && program2Flag == true) //take actions based on the state of the action flag
  {
    fade();

  }

  else
  {
    digitalWrite(blinkLedPin, LOW);

  }

  // save the reading. Next time through the loop, it'll be the lastButtonState:
  lastButtonState1 = reading1;
  lastButtonState = reading;






}
//**************************************


void blink()  //function to blink an LED if the blink period has ended
{
  if (currentMillis - blinkStartMillis >= blinkPeriod)  //test whether the period has elapsed
  {
    digitalWrite(led, !digitalRead(led));  //if so, change the state of the LED
    blinkStartMillis = currentMillis;  //IMPORTANT to save the start time of the current LED state.
  }
}

void fade()    //function to fade an LED
{
  if (currentMillis - fadeStartMillis >= fadePeriod)  //test whether the period has elapsed
  {
    analogWrite(led, brightness);    //set the brightness of the LED
    brightness += increment;    //will wrap round because brightness is an unsigned data type
    fadeStartMillis = currentMillis;  //IMPORTANT to save the start time of the current LED state.
  }
}


Why are you using the same pin ?

1 Like

Well, I should have only use one LED and one name... Sorry about that...

Does your sketch compile ?

Try this:

//  Version    YY/MM/DD     Description
//  1.00       21/10/08     Running sketch

//***********************************************************************************
#define LEDon                     HIGH
#define LEDoff                    LOW

#define SWITCHreleasd             HIGH
#define SWITCHpressed             LOW

#define ENABLED                   true
#define DISABLED                  false

//***********************************************************************************

const byte startSwitch          = 2;
const byte selectionSwitch      = 3;

const byte program2LED          = 5;
const byte program1LED          = 6;
const byte LEDpin               = 10;
const byte heartbeatLED         = 13;

bool program1Flag               = ENABLED;
bool program2Flag               = DISABLED;
bool actionFlag                 = DISABLED;

byte lastStartSwitchState       = SWITCHreleasd;
byte lastSelectionSwitchState   = SWITCHreleasd;
byte brightness                 = 0;                   //0-255
byte increment                  = 1;

//TIMER stuff
unsigned long currentMillis;
unsigned long heartbeatMillis;
unsigned long switchMillis;
unsigned long blinkStartMillis;
unsigned long fadeStartMillis;

const unsigned long blinkPeriod = 1000;
const unsigned long fadePeriod  = 10;

//***********************************************************************************
void setup()
{
  Serial.begin(115200);
  pinMode(startSwitch, INPUT_PULLUP);
  pinMode(selectionSwitch, INPUT_PULLUP);

  pinMode(program1LED, OUTPUT);
  digitalWrite(program1LED, HIGH);
  bool program1Flag = ENABLED;

  pinMode(program2LED, OUTPUT);
  pinMode(LEDpin, OUTPUT);
  pinMode(heartbeatLED, OUTPUT);

} //END of setup()


//***********************************************************************************
void loop()
{
  currentMillis = millis();

  //*************************************
  //to see if the sketch is blocking,
  //toggle the heartbeat LED every 500ms
  if (millis() - heartbeatMillis >= 500)
  {
    //restart this TIMER
    heartbeatMillis = millis();

    //toggle the LED
    digitalWrite(heartbeatLED, !digitalRead(heartbeatLED));
  }

  //*************************************
  //is it time to read the switches ?
  if (millis() - switchMillis >= 50)
  {
    //restart this TIMER
    switchMillis = millis();

    checkSwitches();
  }

  //*************************************
  if (actionFlag == ENABLED && program1Flag == ENABLED)
  {
    blink();
  }

  //*************************************
  if (actionFlag == ENABLED && program2Flag == ENABLED)
  {
    fade();
  }

  //*************************************
  //other non-blocking code goes here
  //*************************************


} //END of loop()


//********************************************************************************
void checkSwitches()
{
  //*********************************************
  // s t a r t S w i t c h
  byte currentSwitchState = digitalRead(startSwitch);

  //**********************
  //was there a change in state ?
  if (lastStartSwitchState != currentSwitchState)
  {
    //update to the new state
    lastStartSwitchState = currentSwitchState;

    //************
    //is the switch pressed ?
    if (currentSwitchState == SWITCHpressed)
    {
      actionFlag = !actionFlag;

      if (actionFlag == DISABLED)
      {
        digitalWrite(LEDpin, LEDoff);
        brightness = 0;
      }
    }

  } //END of   if (lastStartSwitchState != currentSwitchState)


  //*********************************************
  // s e l e c t i o n S w i t c h
  currentSwitchState = digitalRead(selectionSwitch);

  //**********************
  //was there a change in state ?
  if (lastSelectionSwitchState != currentSwitchState)
  {
    //update to the new state
    lastSelectionSwitchState = currentSwitchState;

    //************
    //are we in program #1 AND is the switch pressed ?
    if (program1Flag == ENABLED && currentSwitchState == SWITCHpressed)
    {
      program1Flag = DISABLED;
      digitalWrite(program1LED, LEDoff);

      program2Flag = ENABLED;
      digitalWrite(program2LED, LEDon);

      //start out at 0
      brightness = 0;

      //restart the TIMER
      fadeStartMillis = currentMillis;
    }

    //*********************************************
    //are we in program #2 AND is the switch pressed ?
    else if (program2Flag == ENABLED && currentSwitchState == SWITCHpressed)
    {
      program1Flag = ENABLED;
      digitalWrite(program1LED, LEDon);
      digitalWrite(LEDpin, LEDoff);

      //restart the TIMER
      blinkStartMillis = currentMillis;

      program2Flag = DISABLED;
      digitalWrite(program2LED, LEDoff);
    }

  } //END of   if (lastSelectionSwitchState != currentSwitchState)


  //*********************************************
  //next switch code
  //*********************************************

} //END of   checkSwitches()


//********************************************************************************
void blink()
{
  //has the TIMER expired ?
  if (currentMillis - blinkStartMillis >= blinkPeriod)
  {
    //restart the TIMER
    blinkStartMillis = currentMillis;

    //toggle LED
    digitalWrite(LEDpin, !digitalRead(LEDpin));
  }

} //END of blink()


//********************************************************************************
void fade()
{
  //has the TIMER expired ?
  if (currentMillis - fadeStartMillis >= fadePeriod)
  {
    //restart the TIMER
    fadeStartMillis = currentMillis;

    //next brightness level
    analogWrite(LEDpin, brightness);
    brightness += increment;            //will wrap round because brightness is an unsigned data type
  }

} //END of fade()

This works, thanks for the help! The heartbeatmillis is really good indication if the code is blocked, will keep that one in mind!

Thanks! @LarryD