Using multiple push-buttons

Hi everyone!

I am working on making a keyboard for an art project, so I need about 40 to 50 keys, each being a push button. EDIT: My keyboard is double-sided, so one side is ~50 keys, and in total it would be 100 keys.

I tried to search around for ways to using multiple buttons, and I have referenced to several posts in the community already - link 1, link 2, link 3, and also to adafruit's tutorial here as well as to this page that's in Spanish.

I have tried adafruit's tutorial and it worked, but because she uses analog pins, I would not have enough to work with (since I would need about 40-50 80-100 pins).

I am using an Arduino Mega 2560, so I do have enough digital pins to work with. (I'll probably use two Megas and will cross-wire them together) adafruit's tutorial also includes debouncing, which I don't want because I think it's a bit complicated. I just want to do something simple, as in like the code I wrote so far:

const int button1 = 2;
const int button2 = 3;
const int button3 = 4;

void setup()
{
    pinMode(button1, INPUT);
    pinMode(button2, INPUT);
    pinMode(button3, INPUT);
    Serial.begin(9600);
}

void loop()
{
    if(digitalRead(button1)==HIGH){
        Serial.print("A");
        delay(200);
    }
    else if(digitalRead(button2)==HIGH){
        Serial.print("B");
        delay(200);
    }
    else if(digitalRead(button3)==HIGH){
        Serial.print("C");
        delay(200);
    }
}

but, I had very weird results (the Serial Monitor did not print the correct letter at times).

I think it is because I had only used one resistor (I'll try to upload a picture of how I wired it). The Spanish page that I linked to above uses one resistor for each button, which is probably why mine did not work. However, I am wondering if it IS possible to use only one resistor though, or do I really need so many resistors?

I will be trying to work this out using multiple resistors, but I just wanted to ask if there was a way with only one resistor.

Thank you to everyone in advance!


Note:

I've also tried to use the Button library for my project, but I had a problem (I think with the PULLUP), so unfortunately I couldn't use that library. I have made a post about it in the Installation & Troubleshooting section of the forum, so if anyone could help with that as well, then it would be greatly appreciated!

You need to use the Keypad library.

You can read 64 key with only 5 pins and 4067 analog multiplexer and 8 capacitors and 8 resistors. it works like this:

Select Row
Make datapin output with high level
Make datapin input //now the capacitor on the selected row is charged
Scan through all columns for a high value
Select same row
Make datapin output with low level//discharge capacitor
repeat with next row

I did make this work long time ago on a AVR 2313 in assembler but i dont think i have the code anymore.

EDIT: forgot the schematic, sorry.

You don’t need any resistors. You can use the KeyPad library. You will need to make a circuit like the attached schematic.
The schematic shows a 56 key keypad, but you can make it any number you want. This one has 7 rows and 8 columns. a 49 key pad could have 7 rows and 7 columns, and so on. each row connects to a pin, and each column connects to a pin.

Using the KeyPad library, you configure the number of keys, what pins they attach to, the value that’s generated when you press each key. You then call a function called get_key(), and if a key is pressed, it’s value will be returned.

Keypad Matrix.gif

Another alternative would be to attach a diode to each key. Then you could charlieplex your matrix of keys. This would need only 8 pins for up to 56 keys or 7 pins for up to 42 keys. The only other components needed would be a pullup resistor for each pin, or use internal pullups.

Paul

I am using an Arduino Mega 2560,

So you have 16 Analog inputs, you COULD use the multiple-resistor approach: ArduinoInfo.Info WIKI Like This:

Wow, thank you everyone so very much for your replies!

At first, I was worried about the analog pins, because some comments in the posts that I have looked at said something about different temperatures having an effect , which wouldn’t be so good - though it’s not like my project is too complex anyway (hopefully!).

nilton61:
You can read 64 key with only 5 pins and 4067 analog multiplexer and 8 capacitors and 8 resistors.

Unfortunately I think that is a bit too complicated for my simple mind, as I’m not sure what a multiplexer is and I don’t think there is a need to use capacitors for what I’m doing (just something simple …).

PaulRB:
Another alternative would be to attach a diode to each key. Then you could charlieplex your matrix of keys. This would need only 8 pins for up to 56 keys or 7 pins for up to 42 keys. The only other components needed would be a pullup resistor for each pin, or use internal pullups.

That sounds like a great alternative that uses very little pins – would simplify everything so much – but however I think again that is a bit complex for me…

terryking228:
So you have 16 Analog inputs, you COULD use the multiple-resistor approach: ArduinoInfo.Info WIKI

I’m not so sure that I will work with this, because I don’t really understand it (though it is much more simple compared to the two other approaches above!). It is really simplified though - I’m just not understanding the read_keyboard() function, how those values are gotten for the if-statements.

lar3ry:
You don’t need any resistors. You can use the KeyPad library.

HazardsMind:
You need to use the Keypad library.

I think the way to go would be with the Keypad library. I’m not even sure how I missed such a great tool.

Thank you sincerely to everyone again for the advice and tips. I’ll be posting updates on progress! I haven’t had time to work on this yet, but will definitely get around to it this evening. :slight_smile: Again, much kudos to you all.

EDIT: I just looked at the keypad library briefly (I have to leave soon), and I think I will be needing some additional help with wiring and such. :S Apologies for the bother, but I definitely will try to work with this! Thank you everyone!

Hi everyone,

I have been using the Keypad library, and though I am still trying to figure out with the rows and columns, I think this will work really well ... A big thank you to everyone for this and the other suggestions.

Also, sorry for double posting, but I have come across some issues (nooo...!)

  1. I realized I have made a mistake in explaining about my keyboard (so sorry to you all). The keyboard will have 50 keys, and it is double-sided (it will be standing up, so two people are communicating to each other by typing on this keyboard), so actually there are 100 keys in total.

...which is a huge problem. The Mega 2560 has 54 pins, so if I have two boards, then that would be fine (one board for each side) The problem though, is that since I'll be using two boards, the messages won't be displayed perfectly in 1 single output monitor. I wanted to display the conversation of two people, and this was fine using just 1 board (hit "enter" key once person 1 is done, so a new message is on the next line which indicates person 2's message, and so on, so that a conversation is displayed). But now with 2 boards, I really am unsure about this working out. Is there a way to somehow connect the input from these two boards together?

^This also ties in to my second question:

  1. Is there a way to save the outputs from the Serial Monitor? I would like to record the messages that is being typed from the keyboard.

I have been using "Serial.print(key)" to print the messages to the Serial Monitor, but I would also like to save these messages somehow too. I've been searching for solutions, and there are a few ways I have looked into so far: by using Processing (I would rather not -- don't want an extra program opened), Hyperterminal, gobetwino, or using Arduino's Logger library with MegunoLink. I'm not sure which is the easiest and simplest method -- maybe hyperterminal or gobetwino, but, which would you suggest?

I suspect the solution to my 1st question can be, or is at least connected to, the solution to my 2nd question... but in what ways, I am unsure and am very worried about this as I am in a deep situation now... I think, if there is just no possible way to get around to this, then I'll just reduce my keyboard to just 50 keys in total so that I only need one Arduino board. But -- I really, really am hoping and crossing my fingers for a solution.

As always, thank you all very much for your help, and so sorry that I tend to write so much.

I really am unsure about this working out. Is there a way to somehow connect the input from these two boards together?

You can easily do that via a Serial connection, cross wire them, but don't use Serial1 "Serial"on the first keyboard, you'll need that for the serial monitor.

Is there a way to save the outputs from the Serial Monitor? I would like to record the messages that is being typed from the keyboard.

There was a way to do it using the command prompt, but since I have Windows 8, I can't do it any more due to security reasons. Maybe someone else found a way around that issue.

HazardsMind,

Thank you very much for your quick reply. Your response puts me (somewhat more) at ease since it sounds like there is a workable solution. :)

I'm not sure how to cross wire, so I googled that just now and pulled up a post that said:

"Just cross wire the Arduinos, GND to GND, Tx to Rx and Rx to Tx. Then use the usual serial commands as if you were using the Serial Monitor."

Would I just wire it as the above says to?

I think if the two inputs can be logged into 1, then the second question I have about saving / recording them will follow easily.

Thank you sincerely!

Would I just wire it as the above says to?

Yea, it's just three wires.

Serial works both ways, send and receive, so you can a message to the other arduino, and if you receive a message, you can simple add the persons name in front of it then display it. Ex. Serial.print("John: "); Serial.print(message);

Or you can use the sprintf function to combine both into one and display the buffer, but that just a little over kill, just a little.

HazardsMind: Yea, it's just three wires.

!!! I am so excited to hear this solution (I'll have to get the second Mega to be able to test this out, don't it have yet)

BUT, two questions:

There's 4 GND's on the Mega, so I would still have to connect all of them to each other, right? (so then it's more than 3 wires)

When you say to "not use Serial1 on the first keyboard" ... what do you mean by Serial1?

(Bowing down to your quick responses)

edit: saw your edit -- I actually really wanted to include names to differentiate between the two users, but there might be confusion that would go on and somehow person 1 would become person 2 -- so for my project it would suffice to just have the users enter on a new line... :sweat_smile:

All the grounds are tied together, so anyone of them will work.

You can also use this method: http://forum.arduino.cc/index.php/topic,141978.0.html it requires 8 IO ports and 16 diodes.

HazardsMind: All the grounds are tied together, so anyone of them will work.

Alright, then aside from avoiding Serial1 (aka pins 18 and 19?) and wiring them together, then ... hopefully this will be alright!! :D

jkj56: You can also use this method: http://forum.arduino.cc/index.php/topic,141978.0.html it requires 8 IO ports and 16 diodes.

Thank you jkj56 for your post! Though charlieplexing is a bit complex for me, I don't think I will be able to make my keyboard that way. But, thank you for helping!

I will be working on this tomorrow (must sleep now) and will update on my progress. I am confident to bring good news to you all - I won't let any of you down with the amount of help that I've got.

Thanks!

I fixed my post. Being that you want to use the serial monitor, don’t send or receive the messages from the other Arduino using “Serial”, but Serial1,2 and 3 are fine to use.

Thank you again HazardMind :slight_smile:

With regards to the Keypad library, I have yet another question to ask you amazing folks… :drooling_face:

I realize I do not understand how to make a circuit as in like lar3ry’s post // how to wire the keypad. :~

I’ve modified lar3ry’s 7x8 keypad picture to my 5x10 keyboard, with how I’m thinking or understanding of connecting things (the pins are set randomly, and my letters/numbers/etc are placed just in succession for now).

ROWS:
pin 22 - pin from A, B, C, D, … J connected
pin 24 - pin from K, L, M, N, … T connected
pin 26 - pin from U, V, W, X, … 3 connected
(and so on)

COLUMNS:
pin 32 - pin from A, K, U, 4, and , connected
pin 34 - pin from B, L, V, 5, and . connected
pin 36 - pin from C, M, W, 6 , and : connected
(and so on)

Somewhere along the lines I know these push buttons have to be connected to GND, but I’m not sure from where they would connect. I’m assuming at the end… … …

I have a feeling I know I’m reading the schematic wrong… could anyone provide some pointers please? :blush:


An aside:
I was Googling around Keypad, and I see that already-manufactured keypads have pins at the bottom of it. Since I am making mine manually, I don’t have that – like the “1…14” at the bottom of this picture:

I am wondering if I am supposed to make my keyboard to have something like those pins at the bottom?

Your schematic is correct, and no you don't need to ground them, the library takes care of everything. Wire it the way it is in your picture, and it should work fine.

The easiest way to wire them up is to mount them wherever you want them, and run the wires to each pin in one row. So your first wires would connect to one pin on switches A, B, C, D… etc. You would do the same with ROW 1, then Row 2, and so on. It doesn’t matter which pin on the switches you connect (as long as there are only two connectors or terminals on the switches, or if there are three or more, as long as you connect to a Normally Open terminal).

Once you’ve wired all the rows, wire theremaining switch terminals to each column, so, for example, you now connect switches in the columns; A, K, U,… etc. , then B, L, V… and so on.

Each row and column will connect to the appropriate pin, and as HazardsMind says, no grounds are involved.

The way the library works is that each row is selected, one at a time, by writing, say, a 0 to that row pin, and then checking each colum pin for a 0. When it finds a 0, the button is identified as being the one at the intersection of that row and that column.

Hi everyone,

Just wanted to update with the results of my project. It turned out well and the buttons all worked with the Keypad library.

Thank you to everyone who helped out! It was really, really appreciated.

Much regards. =)