Menu Driven Program

Hi

Im in the process of building and automatic toilet cistern valve tester.

It basically consists of a linear actuator, LCD, and a couple of switches.

I am stuck trying to implement the sceen. The menu will have 6 options which have to be set before the actuator starts testing.

Menu Below

  1. Fill Delay Time
  2. Ram Delay Time
  3. Ram Pulse Time
  4. Start
  5. Pause
  6. Stop

obviously the pause and stop commands will have to run during the void loop() part of the code and opt 1, 2 & 3 could run in the void setup() part of the code. The pause function will have to not interupt the current ram cycle.

Below is my current code with static variables for opt 1,2 3.

int FRPin =  8;   
int MotorPin = 7;

int FillDelay = 10000;
int RamDelay = 500;
int RamPulse = 2000;
int TCount;
int Cycles = 10;

void setup()   {  
  Serial.begin(9600);
  Serial.println("Testing Rig V1.0");
  Serial.println("");
  
  pinMode(FRPin, OUTPUT);   
  pinMode(MotorPin, OUTPUT); 
  
  //Pull Ram in fully
  Serial.println("Retracting Ram");
  digitalWrite(MotorPin, HIGH);
  digitalWrite(FRPin, LOW);
  delay(6000);
  digitalWrite(MotorPin, LOW);
}


void loop()                     
{
  for(int i=0; i<Cycles; i++){
    
    
    //Turn on Motor then push out for RamPulse Time
    Serial.println("Extending Ram");
    digitalWrite(MotorPin, HIGH);   
    digitalWrite(FRPin, HIGH);
    delay(RamPulse);
    
    //Hold the motor for RamDelay Time (-- PUSH OUT--)
    Serial.println("Holding Ram");
    digitalWrite(MotorPin, LOW);
    delay(RamDelay);
    
    //Turn on Motor then pull in for RamPulse Time
     Serial.println("Retracting Ram");
    digitalWrite(MotorPin, HIGH);   
    digitalWrite(FRPin, LOW);         
    delay(RamPulse);
    
    //Hold the motor for RamDelay Time (--PULL IN--)
    Serial.println("Holding Ram");
    Serial.println("");
    digitalWrite(MotorPin, LOW);
    delay(FillDelay);
    
    //test code
    TCount++;
    Serial.println(TCount);
  }
}

The LCD im using is a sparkfun Serial Enabled 16x2 LCD - Black on Green 5V.

Any help on how to impletmen this would be great.

thanks ben

Two things will help: "finite state machine" and "blink without delay".

Thanks for the tips :smiley:

the problem Im having is not really anything to do with the lcd its more of the button press detection.

Sorry I should have explained this better!!

I have 3 buttons <Back, >Foward & OK buttons

I need to know the correct way of detecting button press's for 3 buttons(currenty Im using the arduino example way) and when to poll them and not cause any interferance to the loop part of the code.

thanks

Ben

I am new and this might not be what you are looking for but this is what I use to read my analog buttons

butt1=analogRead(button1); //read in button 1
if (butt1 < buttthres){ //if button one is low then button was pushed
//do stuff here
}
butt2..
butt3..

Right, I would say you want to implement a menu code routine.

Ignore the loop code. Stick code at the end of your setup routing to call Menu(); then in the menu, call other sections of code for the different things you want to do.

My code for a 20x4 serial LCD might help you. I was only using one button for moving on an option and holding it for selecting.

void Menu(){                       
  LCDclear();  
  LCDserial.print("Program Menu"); 
  LCDsecond();     
  switch (programnumber) {                  
  case 1:                                
    LCDserial.print("Race Timer"); 
    LCDthird();
    LCDserial.print("Track: ");
    LCDserial.print(distance);
    LCDserial.print("m");    
    break;                               
  case 2:
    LCDserial.print("Reaction Tester");
    break;
  case 3:
    LCDserial.print("Calibration Mode");
    break;
  default:
    LCDserial.print("Race Timer");
    LCDthird();
    LCDserial.print("Track: ");
    LCDserial.print(distance);
    LCDserial.print("m");
  }

  LCDserial.print(0xFE, BYTE);
  LCDserial.print(226, BYTE);
  LCDserial.print("Next >");
  while(digitalRead(starterbutton) == HIGH){}
  delay(5);
  while(digitalRead(starterbutton) == LOW){}
  menudelaycount = 0;
    while(menudelaycount <500){
    delay(1);
    menudelaycount++;
    if(digitalRead(starterbutton) == LOW){
      programnumber++;
    if(programnumber > 3){
      programnumber = 1;
    }
    Menu();
    }
  }
  switch (programnumber) {
      case 1:
        Race();
        break;
      case 2:
        Reaction();
        break;
      case 3:
        Calibration();
        break;
      default:
        Race();
      }
}

The LCDsecond(); is a seperate routine for selecting the LCD line.

The code waits until you press a button. When you press the button it times how long you press it for. If it is longer than a certain time then it 'selects' that option, if not then it moves on one option.

I can help more if you need it.

Mowcius

Hi Mowcius,

Thanks for your help there are a few things I need to clarify.

I like the way you use 1 button!! but when you press the button does it go LOW?

I dont understand how to call this code??

In psuedo code

has button been pressed
   if yes
     menu();
   else
      return();

that would work ok in the loop but how does this work from setup().

Do you just continually loop until its completed??

Sorry if this sounds stupid I just cant get my head around it :-[

and finally ;D where in my code posted above do i call to see if a button has been pressed??

thanks again

Perhaps you could look at this:http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1273349195

Ok, the clarify bits of my code

void Menu(){ //starts the menu subroutine from being called in setup
LCDclear(); //clears the LCD
LCDserial.print("Program Menu"); //prints to the lcd on first line
LCDsecond(); //prints to lcd on second line etc...
switch (programnumber) { //reads the program number (set as 1 in setup)
case 1: //displays the first menu item
LCDserial.print("Race Timer");
LCDthird();
LCDserial.print("Track: ");
LCDserial.print(distance);
LCDserial.print("m");
break;
case 2: //displays the second menu item
LCDserial.print("Reaction Tester");
break;
case 3: //displays the third menu item
LCDserial.print("Calibration Mode");
break;
default: //if errors then it goes to default item is the race code.
LCDserial.print("Race Timer");
LCDthird();
LCDserial.print("Track: ");
LCDserial.print(distance);
LCDserial.print("m");
}

LCDserial.print(0xFE, BYTE); //Command code
LCDserial.print(226, BYTE); //Goes to specific point to display code
LCDserial.print("Next >"); //next code in specific position
while(digitalRead(starterbutton) == HIGH){} //while button is high do nothing: {} (helps with debounce after button has been pressed)
delay(5);
while(digitalRead(starterbutton) == LOW){} //wait until button has been pressed (taken high).
menudelaycount = 0; //clear menu delay
while(menudelaycount <500){ //do this code within the 500 limit (over 500ms because of other stuff that is done and takes time)
delay(1);
menudelaycount++;
if(digitalRead(starterbutton) == LOW){ //if the button goes low (button released) within this loop then it advances one menu option
programnumber++; //increase the menu option
if(programnumber > 3){
programnumber = 1;
}
Menu(); //then run menu code from start: the change in program number makes it change the option it is on.
}
}
switch (programnumber) { //if the button is not let go within the menu time stated above then it does not loop back and then selects the subroutine from this switch case:
case 1:
Race();
break;
case 2:
Reaction();
break;
case 3:
Calibration();
break;
default:
Race();
}
}

The switch is held low by a pulldown resistor, it waits until it is low (in case someone is holding the button), then it then waits for a button press.
When it senses a button press, it starts a looping routine for 500 (not milliseconds due to other things that happen apart from the delay(1); ).
If the button is let go within that time (normal quick press), it advances the menu item on. If it is held the whole time then it takes the program number, gets to the end of the code and runs the selected program.

You probably want to do it with an up/down menu on your 16x2 rather than the 20x4 serial LCD I did it on but the code could be pretty similar.

If you wanted to do it up/down/select then that should not be too difficult either.
Assign each program part a seperate sub-routine and a number, then display the first 2 programs (numbers i and i+1), if you press the down button, advance the i value and run the display routine again. If you press the up button, decrease the i value (unless it is 1) and run again. Upon select button press, read the program number and run a switch case routine to select the corresponding sub-routine.

Hope that helps you,

Mowcius :slight_smile:

Thank Mowcius!!

I have apadapted your code into my program and the mainmenu() sub is working.

I am having problems with the fillMenu() sub. Once I pick a delay time
it types the serial command the same amount of time (code highlighted below)

void mainMenu()
{ 
 //LCDclear();  //clears the LCD 
// Serial.println("Program Menu"); //prints to the lcd on first line -------------------------------------------------------------------------------------------> NOT NEEDED???
// LCDsecond(); //prints to lcd on second line etc... -------------------------------------------------------------------------------------------> NOT NEEDED???
 switch (programnumber) { //reads the program number (set as 1 in setup)
 case 1:            //displays the first menu item              
   Serial.println("Set Fill Delay");
   break;
 case 2:        //displays the second menu item
   Serial.println("Reset Fill Delay");
   break;
 case 3:       //displays the third menu item
   Serial.println("Ram Pulse");
   break;
 case 4:            //displays the first menu item              
   Serial.println("Start"); 
   break;
 case 5:        //displays the second menu item
   Serial.println("Pause");  
   break;
 case 6:       //displays the third menu item
   Serial.println("Stop");
   break;
 default:      //if errors then it goes to default item 
   Serial.println("Fill Delay");
}

 //Serial.println(0xFE, BYTE); //Command code-------------------------------------------------------------------------------------------> NOT NEEDED???
 //Serial.println(226, BYTE);  //Goes to specific point to display code-------------------------------------------------------------------------------------------> NOT NEEDED???
 Serial.println("Next >");    //next code in specific position 
 while(digitalRead(menuButton) == HIGH){} //while button is high do nothing: {} (helps with debounce after button has been pressed)
 delay(5);
 while(digitalRead(menuButton) == LOW){} //wait until button has been pressed (taken high).
   menudelaycount = 0; //clear menu delay
   while(menudelaycount <500){ //do this code within the 500 limit (over 500ms because of other stuff that is done and takes time)
   delay(1);
   menudelaycount++;
   if(digitalRead(menuButton) == LOW){ //if the button goes low (button released) within this loop then it advances one menu option
     programnumber++; //increase the menu option
   if(programnumber > 6){
     programnumber = 1;
   }
   mainMenu(); //then run menu code from start: the change in program number makes it change the option it is on.
   }
 }
 switch (programnumber) { //if the button is not let go within the menu time stated above then it does not loop back and then selects the subroutine from this switch case:
     case 1:
       Serial.println("Fill Func");
       fillMenu();
       break;
     case 2:
        Serial.println("Delay Func");
       break;
     case 3:
        Serial.println("Pulse Func");
       break;
      case 4:
        Serial.println("Start Func");
       break;
     case 5:
        Serial.println("Pause Func");
       break;
     case 6:
        Serial.println("Stop Func");
       break;
     default:
        Serial.println("Default Race");
     }
}

void fillMenu()
{ 
   FillDelay = FillDelay +3000;
   Serial.println(FillDelay);
   
   Serial.println("Next >");    
   while(digitalRead(menuButton) == HIGH){} 
     delay(5);
   while(digitalRead(menuButton) == LOW){} 
     menudelaycount = 0; 
   while(menudelaycount <500){ 
   delay(1);
   menudelaycount++;
   if(digitalRead(menuButton) == LOW){ 
     //programnumber++; 
   if(FillDelay > 120000){
     FillDelay = 0;
   }
   fillMenu(); 
  }
 }
   [glow]Serial.print("Fill Delay set @ ");
   Serial.print(FillDelay);[/glow]
}

Here is my Serial Output (I dont yet have my LCD some Im using Serial insted)

Set Fill Delay
Next >
Fill Func
4000
Next >
7000
Next >
Fill Delay set @ 7000Fill Delay set @ 7000Extending Ram
Holding Ram
Retracting Ram
Holding Ram

as you can see above I pressed the button twice and it prints the serial string twice. If i press the button 3 times it prints the serial string 3 times......

thanks again for all your help

Ben

I will take a look later when I have a little more time so check back in a few hours :slight_smile:

Mowcius

thanks

Ok, not quite sure what you want to do exactly now.
This is the menu you want to do:

  1. Fill Delay Time
  2. Ram Delay Time
  3. Ram Pulse Time
  4. Start
  5. Pause
  6. Stop

Just ignore what I said before about one button.
Do you want to have 3 buttons, one left, one right and one select?
Do you want to have 3 buttons, one up, one down and one select?
Or do you want a single scrolling menu on one button (seperate screen change for each item or scrolling up/down?)

The only reason why I used the one button was becuase I was short on I/O pins. If I had had more pins then I would have done a better menu which scrolled up/down, with 3 buttons :slight_smile:

If you want a scrolly up down menu then this is what I am thinking. It will also help me with coding a scrolling menu on my 40x4 LCD so I'm not just doing it for you :stuck_out_tongue: ;D

My idea:
First screen:

Fill Delay <
Ram Delay

After one press of the down button:

Fill Delay
Ram Delay <

After the next press of the down button:

Ram Delay
Ram Pulse <

If you then press the up button:

Ram Delay <
Ram Pulse

If you get to the botton of the menu:

Stop <


Maybe make it so if you get to the top it cycles back round to the start..

What do you think?

The code you posted has a load of errors so I am not going to try and correct it at the moment.
You have the basics but I think the type of menu I described above would be more suitable.
If you just want a single button (but not so obvious as to how to use) menu then I can sort out that code for you.
When I get home, I will also have my serial LCD to play on and test with.

Mowcius

Hi Mowcius

That would be GREAT!!!!

I just want to thank you for all your help. I will have my LCD tommorrow too!!

thanks

ben

I presume you are wanting a 2 line up/down scrolling menu then.

I will see what I can do.

Mowcius

Here is my 15 minutes...

It is not very good code wise but it works... Just...

You might need to change the position code for the 16x2 serial LCD but it should help anyway.

#include <NewSoftSerial.h>

NewSoftSerial LCDserial(0, 2);

int prognumber = 1;
int line = 1;

int down = 8;
int select = 9;
int up = 10;

void menu();
void LCDclear();
void LCDfirst();
void LCDsecond();
void LCDmenudisplay();

void first();
void second();
void third();
void fourth();
void fifth();

void setup() {
LCDserial.begin(9600);
menu();
}

void loop() {
//nothing to loop but is required in every sketch.
}

void LCDclear(){
LCDserial.print(0xFE, BYTE);
LCDserial.print(0x01, BYTE);
}

void LCDfirst(){
LCDserial.print(0xFE, BYTE);
LCDserial.print(128, BYTE);
}
void LCDsecond(){
LCDserial.print(0xFE, BYTE);
LCDserial.print(192, BYTE);
}

void menu() {
while(digitalRead(up) == HIGH or digitalRead(down) == HIGH or digitalRead(select) == HIGH){};
delay(50);
LCDclear();
LCDfirst();
if(prognumber > 1){
prognumber--;
}
else{
prognumber == 1;
}
LCDmenudisplay();
LCDsecond();
prognumber++;
LCDmenudisplay();
if(line == 1){
LCDserial.print(0xFE, BYTE);
LCDserial.print(143, BYTE);
LCDserial.print("<");
}
else {
LCDserial.print(0xFE, BYTE);
LCDserial.print(207, BYTE);
LCDserial.print("<");
}
while(digitalRead(up) == LOW && digitalRead(down) == LOW && digitalRead(select) == LOW){}
if(digitalRead(down) == HIGH){
line++;
if(line > 2){
line = 2;
prognumber++;
if(prognumber > 4){
prognumber = 5;
}
}
menu();
}
else if(digitalRead(up) == HIGH){
line--;
if(line < 1){
line = 1;
prognumber--;
}
menu();
}
else if(digitalRead(select) == HIGH){
if(line == 1){
prognumber--;
}
switch (prognumber) {
case 1:
first();
break;
case 2:
second();
break;
case 3:
third();
break;
case 4:
fourth();
break;
case 5:
fifth();
break;
default:
first();
}
}
}

void LCDmenudisplay() {
switch (prognumber) {
case 1:
LCDserial.print("First");
break;
case 2:
LCDserial.print("Second");
break;
case 3:
LCDserial.print("Third");
break;
case 4:
LCDserial.print("Fourth");
break;
case 5:
LCDserial.print("Fifth");
break;
default:
LCDserial.print("First");
}

}

void first() {
digitalWrite(13, HIGH);
menu();
}

void second() {
menu();
}

void third() {
menu();
}

void fourth() {
menu();
}

void fifth() {
digitalWrite(13, HIGH);
delay(1000);
digitalWrite(13, LOW);
menu();
}

Mowcius

the void first(){ } etc are where you would stick the pieces of code.

No doubt someone can write something much better (and so could I with more time and less tiredness).

The newsoftserial could be changed to the softwareserial library with no problems but the newsoftserial library is better...

I was testing it using the top 2 lines of my 40x4 so that is why the positioning is probably off for the second line text...

The code basically does what I explained a few posts up but you will see if you try it.
Look at serial LCD datasheet to find out the positioning values for the 16x2 LCD.

Mowcius

You still around reading this?

Mowcius

Hi Mowcius Sorry Yes Im still reading this I have been away and haven't had a chance to come back here.

I have been playing with the first code you gave me ( 1 Button) and I have it working fully.

Do you mind having a quick look to see if there are an obvious errors/problems.

/* Menu Code by Adapated from Mowcius Code
*/

#include <NewSoftSerial.h>
#include <EEPROM.h>

NewSoftSerial LCDserial(0, 3);


// START Menu Stuff
int menuButton = 2;    
int programnumber = 1;
int menudelaycount = 0;
int menudelaycount2 = 0;
// End Menu Stuff

long ramCycle = 0;

int FRPin =  8;   
int MotorPin = 7;

long fillDelay = 1000;
long holdDelay = 500;
int ramPulse = 500;

void setup()   {  
  LCDserial.begin(9600);
  Serial.begin(9600);
  LCDclear();
  selectLineOne();
  LCDserial.print("Azzurra Bathroom");
  selectLineTwo();
  LCDserial.print("Testing Rig V1.0");
  delay(5000);
  pinMode(menuButton, INPUT);
  
  pinMode(FRPin, OUTPUT);   
  pinMode(MotorPin, OUTPUT); 
  
  //Pull Ram in fully
  retractRam();
  
  mainMenu(); 
}

void loop(){
}


void start()                     
{
  delay(3000);
  while(digitalRead(menuButton) == LOW){
    
    LCDclear();
  
    //Turn on Motor then push out for ramPulse Time
    selectLineOne();
    LCDserial.print("Extending Ram");
    digitalWrite(MotorPin, HIGH);   
    digitalWrite(FRPin, HIGH);
    delay(ramPulse);
    checkPress();
    
    //Hold the motor for holdDelay Time (-- PUSH OUT--)
    LCDclear();
    selectLineOne();
    LCDserial.print("Holding Ram");
    digitalWrite(MotorPin, LOW);
    delay(holdDelay);
    checkPress();
    
    //Turn on Motor then pull in for ramPulse Time
    LCDclear();
    selectLineOne();
    LCDserial.print("Retracting Ram");
    digitalWrite(MotorPin, HIGH);   
    digitalWrite(FRPin, LOW);         
    delay(ramPulse);
    checkPress();
    
    //Hold the motor for holdDelay Time (--PULL IN--) & Print Current Ram Count
    LCDclear();
    selectLineOne();
    LCDserial.print("Holding Ram");
    digitalWrite(MotorPin, LOW);
    ramCycle++;
    LCDclear();
    selectLineOne();
    LCDserial.print("Ram Count   ");
    selectLineTwo();
    LCDserial.print(ramCycle);
    delay(fillDelay);
    checkPress();
    
  }
 
}

void retractRam()
{
  LCDclear();
  selectLineOne();
  LCDserial.print("Retracting Ram");
  selectLineTwo();
  LCDserial.print("to Home Position");
  digitalWrite(MotorPin, HIGH);
  digitalWrite(FRPin, LOW);
  delay(6000);
  digitalWrite(MotorPin, LOW);
}

void mainMenu()
{ 
 LCDclear();  //clears the LCD 
 selectLineOne();
 switch (programnumber) { //reads the program number (set as 1 in setup)
 case 1:            //displays the first menu item              
   LCDserial.print("Set Fill Delay");
   break;
 case 2:        //displays the second menu item
   LCDserial.print("Hold Delay");
   break;
 case 3:       //displays the third menu item
   LCDserial.print("Ram Pulse");
   break;
 case 4:            //displays the first menu item              
   LCDserial.print("Start"); 
   break;
 case 5:       //displays the third menu item
   LCDserial.print("Stop");
   break;
 default:      //if errors then it goes to default item 
   LCDserial.print("Fill Delay");
}
 selectLineTwo();
 LCDserial.print("Next >");    //next code in specific position 
 while(digitalRead(menuButton) == HIGH){} //while button is high do nothing: {} (helps with debounce after button has been pressed)
 delay(5);
 while(digitalRead(menuButton) == LOW){} //wait until button has been pressed (taken high).
   menudelaycount = 0; //clear menu delay
   while(menudelaycount <500){ //do this code within the 500 limit (over 500ms because of other stuff that is done and takes time)
   delay(1);
   menudelaycount++;
   if(digitalRead(menuButton) == LOW){ //if the button goes low (button released) within this loop then it advances one menu option
     programnumber++; //increase the menu option
   if(programnumber > 5){
     programnumber = 1;
   }
   mainMenu(); //then run menu code from start: the change in program number makes it change the option it is on.
   }
 }
 switch (programnumber) { //if the button is not let go within the menu time stated above then it does not loop back and then selects the subroutine from this switch case:
     case 1:
       //LCDserial.print("Fill Func");
       fillMenu();
       break;
     case 2:
       // LCDserial.print("Delay Func");
        delayMenu();
       break;
     case 3:
        //LCDserial.print("Pulse Func");
        pulseMenu();
       break;
      case 4:
        LCDclear();
        selectLineOne
        LCDserial.print("Starting Test");
        start();
       break;
     case 5:
        LCDserial.print("Stop Func");
       break;
     default:
        LCDserial.print("Default Start Func");
     }
}

void fillMenu()
{ 
   LCDclear();
   selectLineOne();
   LCDserial.print(fillDelay);
   selectLineTwo();
   LCDserial.print("Next >");    
  
   while(digitalRead(menuButton) == HIGH){}
     delay(5);
   while(digitalRead(menuButton) == LOW){} 
     menudelaycount = 0;
   while(menudelaycount <500){
     delay(1);
     menudelaycount++;
     if(digitalRead(menuButton) == LOW){ 
        fillDelay = fillDelay +3000; 
     if(fillDelay > 120000){
       fillDelay = 0;
     }
   fillMenu();
   }
 }
   LCDclear();
   selectLineOne();
   LCDserial.print("Fill Delay set @ ");
   selectLineTwo();
   LCDserial.print(fillDelay);
   delay(3000);
   mainMenu();
}

void delayMenu()
{ 
  LCDclear();
  selectLineOne(); 
  LCDserial.print(holdDelay);
  selectLineTwo();
  LCDserial.print("Next >");    
  
   while(digitalRead(menuButton) == HIGH){} 
     delay(5);
   while(digitalRead(menuButton) == LOW){} 
     menudelaycount = 0; 
   while(menudelaycount <500){ 
     delay(1);
     menudelaycount++;
     if(digitalRead(menuButton) == LOW){ 
        holdDelay = holdDelay +500;
     if(holdDelay > 60000){
       holdDelay = 0;
     }
   delayMenu();
   }
 }
   LCDclear();
   selectLineOne();
   LCDserial.print("Hold Delay set @ ");
   selectLineTwo();
   LCDserial.print(holdDelay);
   delay(3000);
   mainMenu();
}

void pulseMenu()
{ 
   LCDclear();
   selectLineOne();  
   LCDserial.print(ramPulse);
   selectLineTwo();
   LCDserial.print("Next >");    
  
   while(digitalRead(menuButton) == HIGH){} 
     delay(5);
   while(digitalRead(menuButton) == LOW){} 
     menudelaycount = 0; 
   while(menudelaycount <500){ 
     delay(1);
     menudelaycount++;
     if(digitalRead(menuButton) == LOW){
        ramPulse = ramPulse +250; 
     if(ramPulse > 6000){
       ramPulse = 0;
     }
   pulseMenu(); 
   }
 }
   LCDclear();
   selectLineOne();
   LCDserial.print("Ram Pulse set @ ");
   selectLineTwo();
   LCDserial.print(ramPulse);
   delay(3000);
   mainMenu();
}

void checkPress()
{
  if (digitalRead(menuButton) == HIGH)
  {
    retractRam();
    LCDclear();
    selectLineOne();
    LCDserial.print("Paused");
  //  selectLineTwo();
   // LCDserial.print("Press button to goto menu");    
    delay(500);
    while(digitalRead(menuButton) == LOW){}
    mainMenu();
    
  }
}

void selectLineOne(){  //puts the cursor at line 0 char 0.
  LCDserial.print(0xFE, BYTE);   //command flag
  LCDserial.print(128, BYTE);    //position
}

void selectLineTwo(){  //puts the cursor at line 2 char 0.
  LCDserial.print(0xFE, BYTE);   //command flag
  LCDserial.print(192, BYTE);    //position
}

void LCDclear(){
  LCDserial.print(0xFE, BYTE);   //command flag
  LCDserial.print(0x01, BYTE);   //clear command
  }

Thanks again

Ben

Well not that I can see from a very quick look. If it is working then it is probably ok.

If I get time then I will load up your code on my arduino and LCD later to see what it looks like and if I can suggest any changes/improvments.

If you get the time then you might still want to take a look at the scroling menu I wrote to see if it suits you better.

Mowcius

Hi Mowcius,

thanks Im going to load it up tomorrow to see how it works.

thanks

Ben