Changing function state from inside a if-loop? [Solved]

I'm building a ATtiny85-based control and reset-circuit for my Raspberry Pi and the attached HD44780-LCD. It's meant to turn the LCD on or off and trigger a reset to wake the Pi up from shutdown, but the reset should only be possible if the LCD is turned off. After resetting the Raspberry Pi the LCD should turn on by itself. Should be simple, but that's where I'm stuck. I tried a lot of stuff, but I just cant figure out what I'm doing wrong here. The sketch is working, but how do I get the LCD to turn on after triggering the reset?

Here's my sketch:

int push = 3;                   // LCD on/off button
int val;                        // variable for reading pin 3s status
int val2;                       // variable for reading pin 3s status
int buttonState; 
int LCDMode = 0;                // LCD on/off 
int gndSwPin = 2;               // transistor for LCD grounds

int ledPin = 0;                 // Blinkenlight

int rstBtn = 4;                 // button for rPi reset circuit
int rstOut = 1;                 // transistor for rPi reset circuit

int value, value2 ;             // fade for Pin 0 LED
long time=0;                    // fade for Pin 0 LED
int periode = 2000;             // fade for Pin 0 LED

void setup()
{
  pinMode(rstOut, OUTPUT);     // reset transistor
  pinMode(rstBtn,INPUT);       // pin 4 button
  digitalWrite(rstBtn,HIGH);   // internal pullup

  pinMode(push,INPUT);         // LCD on/off button
  pinMode(gndSwPin, INPUT);   // transistor for LCD grounds
  pinMode(ledPin, OUTPUT);     // Blinkenlight
  digitalWrite(push,HIGH);     // internal pullup
}

void loop()
{
  int mode;                                // LCD on or off
  mode = chkbtn();                         // see below

  if (mode == 0) {                         //LCD off
    int rstState = digitalRead(rstBtn);    //reset pulse
    if(rstState == LOW){                   //reset pulse
      digitalWrite(rstOut,HIGH);           //reset pulse
      delay(40);                           //reset pulse
    }
    else{
      digitalWrite(rstOut,LOW);              // don't reset
      digitalWrite(gndSwPin, LOW);           // LCD off
      digitalWrite(ledPin, LOW);             // LED off
    }
  }

  if (mode == 1) { 
    digitalWrite(gndSwPin, HIGH);        //LCD on
    int ledVal;                          //LED fade
    ledVal=fade();                       //LED fade
    analogWrite(ledPin,ledVal);          //LED fade
  }

}

int chkbtn(){                          // state for LCD

  val = digitalRead(push);             // read input value and store it in val
  delay(10);                           // 10 milliseconds is a good amount of time
  val2 = digitalRead(push);            // read the input again to check for bounces
  if (val == val2) {                   // make sure we got 2 consistant readings!
    if (val != buttonState) {          // the button state has changed!
      if (val == LOW) {                // check if the button is pressed
        if (LCDMode == 0) {            // if its off
          LCDMode = 1;                 // turn LCD on
        } 
        else {
          if (LCDMode == 1) {          // if it's on
            LCDMode = 0;               // turn LCD off
          } 
        }
      }
    }
  }
  buttonState = val;                   // save the new state in variable
  return LCDMode;
}

int fade(){                            // LED fading stuff
  unsigned long currentMillis = millis();

  time = millis();
  value = 128+127*cos(2*PI/periode*time);
  value2 = 128+127*cos(2*PI/periode*(0-time));
  analogWrite(ledPin, value); 
  return value;  
}

just had a very quick glance of your code but here is a starting point:

you should perhaps remove val1 and val2 from your main body of the program and put them in your "chkBtn" function as they are not required in the rest of the program thus keeping it in scope, you should also change LCDMode to "volatile int LCDMode = 0;" thus telling the compiler not to use temporary register addresses for this and load it directly from RAM.

zx

As the LCD is attached to the Pi should it not be the Pi that turns it on ? The Arduino could look at a pin on the Pi to determine if it is active or not. I presume that you want to prevent the Pi from being reset if it is already running,

I bet that there's a way to turn the LCD off via the Pi, but to achieve that I need to learn how to write programs for it, and I'm already struggling here. Also it's meant to work with every Pi after configuring Lcdproc. And yes, it's purposed to avoid accidental resetting. Oh, and please forgive the missing vowels in my sketch; that's an old habit from long gone years :slight_smile:

Could it be as simple as setting mode to 1 after this?

    delay(40);		//reset pulse

That was the first thing i tried. Sadly it's not that easy.

Oh yes, LCDMode immediately puts it back. Try this there instead:

LCDMode = 1;

Not a pretty solution though.

Ok, I applied the changes zx81 proposed and also those from wildbill:

if(rstState == LOW){                   //reset pulse
      digitalWrite(rstOut,HIGH);           //reset pulse
      delay(40);                           //reset pulse
      LCDMode = 1;
      digitalWrite(rstOut,LOW);           //reset pulse
    }

Works like a charm now! Yay! :slight_smile:
Thanks for helping to all of you!