I am working on a project using my Arduino mega2560 that triggers a solenoid (maximum of three solenoids), my camera and my flash (maximum of two flashes). The core routine is there, and working.

Now I want to refine this by adding a menu and 16x2 LCD with 6 buttons (up/down/left/right/select/reset). This is meant to be so the user can change the default values for:
- the amount of solenoids to be used (max 3),
- the amount of drops per solenoid (max 3),
- the time between drops and
- the time between active solenoids.
The layout of the menu is there, but not yet coded.

My default values for solenoids used, droplet size, droplet timing, solenoid timing, camera delay and flash(es) delay(s) are put in an array. Through the menu the default values will be presented to the user. He can accept (select button) or change the value within certain limits using the up/down buttons.

The question is, what is an easy (for a beginner like me) to program way to accept user input and store this in the array, overwriting the presented default value? I also would like to have the possibility for the user to back out of a menu option and leave the default setting of the specific submenu value.

I was thinking of creating a shadow array with blanks, to be filled in by the user and copy all the values to the array that will be used by the core routine. Another line of thinking leads me to just abandoning the array and making use of a bunch of variables. As you will probably see, I need some advice here.

Thanks very much for reading and your advice, happy to answer questions that may help clarify the issue.

Regards, Kiezel


Your hardware side for the user to use can be based on an ADC type keypad pictured below, this only uses one pin and is pretty reliable. Note that not all code is given or design as it would be useless for learning and I also put effort into the code this came from, logic helps with the rest of each part... enter image description here

The code is pretty simple:

You would write a function like so~

char keypad(int in){

if(in < 949){
    if(in > 935){
        return 's'; //select


else return = 0;

Next would be the code for the menu, you could hold the default values in an array and then modify them in the code, with set positions for defaults, considering

My default values for solenoids used, droplet size, droplet timing, solenoid timing, camera delay and flash(es) delay(s) are put in an array.

Example from one of my projects

//Menu levels
#define level0 0
#define level1 1
#define level2 2
//master level of current point
#define mlevel 6        
#define msub_level 7
#define sub_level1 0
#define sub_level2 1
#define sub_level3 2
#define sub_level4 3
#define sub_level5 4
// default level on boot
uint8_t current_level = mlevel;

Next would be to push the data to

int navigate(char key){
if(key == 'u'){
        if(current_level == mlevel){
        if(count == 3){ //roll-over

            count = 0;
            //update LCD....
        else count++;
        //update LCD....

    if(current_level == msub_level){

        if(count == 5){//roll-over

            count = 0;
            //update LCD....
        else count++;
        //update LCD....

//..... other ones here

    return count;

You would use the returned count to find the relative place in your array. e.g:

int default[n] ={x,y,z,...};

get the key > put into navigate() > put into dafault[count];

You would also change the default after

  • It has been changed or,
  • The key has been debounced, i.e. use logic to determine if the key has changed state or,
  • The user has chosen 'accept'

Update of the LCD can be done at the points you want it done

  • His Arduino has 54 digital I/O pins. Doesn't really need your pin-saving ADC trick. Mar 5 '15 at 12:15
  • @edgar - Meh I see your point, user wanted 'simple'. He can search google for IO scanning libraries. And the method of the rest of the UI could still stand.
    – RSM
    Mar 5 '15 at 12:20
  • Okay, this is good! I use one of the common libraries for the 1602 LCD shield with buttons, so that part is covered. I also have found (and digested) a debounce routine. It works. Same goes for the menu part, I like the solution for presenting the input/changed values. I don't understand the part for pushing the input data into the array. Would you please be so kind and elaborate on this? Thanks a lot!
    – Kiezel
    Mar 9 '15 at 20:04
  • @Kiezel - the returned variable count from navigate() is an int therefore it is put into the array to index a specific point in the array. You would use another if,else set to change if the user is in the main or sub menu (if you used the same method presented). That way you would need to create the two arrays, sub, array and main` array. please let me know if this helped, I might have confused it more ;)
    – RSM
    Mar 9 '15 at 20:40
  • @RSM - Thanks, I understand the concept, input is grasped as a variable count and put into a sub-array. I guess I can use the sub-array with the changed variables to deliver the input for my main routine. But how to handle the situation where the default value is correct and not changed or committed by the user? In my preferred situation I know exactly where the user is in the menu. And when a value changes the new value will be put into the array in the correct "slot" for later use. It could be that your solution is doing just that, but I don't get it yet.
    – Kiezel
    Mar 10 '15 at 19:10

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.