Help with Arduino Uno

Hello Everybody. First off I am new and glad to be here. I am impressed with the amount of knowledge provided from everybody on this forum. I have an electronics background to an extend and a pretty vast programming background. However I have little to no experience working with the hardware aspect of things, but willing to learn. :slight_smile:
I bought the Arduino Uno starter kit with an idea in hand that I would like to bring to fruition. I am not sure if I have the required hardware needed to build this, or if this idea is even feasible. I turn to the wonderful knowledgeable folks on this forum to shed some light. I will do my best to explain what I am trying to accomplish, bare with me.

What I am trying to accomplish
I have 1 Arduino board with an LCD display.
In the next room I have 24 normally open switches. Essentially just 24 separate pairs of wire.
The plan is to be able to close one circuit thus pushing the button/switch, and then have the
display read out which button it is.
Example; Push button, then LCD reads "Switch #1 Closed" or "Switch # 9 Closed" ect.
Thats pretty much it...
I thought about going the analog route. Using 24 different valued resistors. Basic ohms law.
Or maybe there is a better way using 24 slave boards. But they would all have to have a unique address or something. Not sure how that works.
Thats pretty much all i got....Im hoping someone out there has an Idea and willing to share their thoughts. Thanks everyone.

How long will the wires be between the Arduino and the switches?

anywhere between 50-200 feet.Cable resistance obviously would have to be taken into consideration if going the analog path. I just feel like there is a better way to do it. Like maybe RS232 or something

The simplest thing would be to get an Arduino Mega (54 I/O pins).

The "right way" is probably some multiplexer chips. (Sorry, I don't have a specific recommendation.) A multiplexer switches between inputs... For example, there is only one analog-to-digital converter inside the ATmega chip but there are multiple analog inputs and a multiplexer in the chip so your Arduino can have multiple analog inputs.

I thought about going the analog route. Using 24 different valued resistors

That can work but personally I hate using analog when everything is really digital (the switches are digital and the data is digital).

You can use port extenders to connect the many switches, then run a cable to the Arduino. With SPI a 5-7 conductor cable will be sufficient to read up to 32 distant switches (2 port expanders with 16 inputs each). You even can use some pins for output, if desired. In code you read 4 bytes from the port extenders, and check each bit whether the related switch is closed.

An analog solution is not suited for so many switches, because it allows for only one switch closed at a time, and because the long cable will add too much distortion to the signal.

Hi See How-To HERE on multiple buttons with resistors.

Wow, 5 replies before I could finish typing this up....

One way would be to use 10 I/O pins to multiplex the switches as 6x4.

AVR (the chips used in most Arduinos) pins can be set as OUTPUT LOW to act as ground, OUTPUT HIGH to source power, INPUT_PULLUP to source power through 20K to 50K ohms internal pullup resistor (such low current makes the pin ground-safe) and INPUT which is electrically neutral when not being read, called the Z-state. Reading an AVR INPUT takes 1 microAmp of current but don't laugh, you can read a digital pin multiple times in a microsecond too.

With the multiplex you need to put a diode on every switch --if you intend to be able to read multiple switches closed at once-- and I would suggest a .1uF cap across every switch to debounce the switches in hardware unless you want to debounce in software and save doing that.

You start with ALL the pins set INPUT and then turn one row ON as OUTPUT HIGH. Then you read each column in turn to see if any switches are closed and then turn the row pin back to INPUT. Repeat row for row and cycle through all the switches continuously.

You could code right in there what to do if a switch is ON or OFF but I recommend that you only set a bit in a 3 byte array and put the event reaction code after the switch read code to keep the indent levels down and be modular.
If the read code maintains indexes for row and column and only reads one switch per pass through loop() then the read code won't make other code inside of loop() wait (called blocking) which lets you have one routine that sets bits and another that reads them and acts leaving room for still more code to "run together/do many things at once" like blink a status led and watch for serial input.
With the non-blocking approach, adding another routine does not require weaving lines into already existing logic and the spaghettification that generally results. Changing from multiplex wiring to using input shift registers would mean rewriting just that one part to set the bits a different way. You hang onto those modules for later projects, it's much cleaner than weaving input, process-output into a single block of code.
I know this because I did both ways for years.

The Arduino software method of void setup() followed by void loop() makes that easy since when the loop() function ends it deals with serial (you can customize this) and runs loop() again. With the non-blocking approach you can achieve loop() running 50K or more times per second so figure that 24 switches can be checked and acted upon at over 2KHz each reading just one per pass.

pert:
How long will the wires be between the Arduino and the switches?

There was a project not long ago where a guy put microswitches at the ends of 25m wires on a very long Hot Wheels track. It turns out that if you're not trying to run much of a frequency over 25m long wires that a 5V pin set INPUT_PULLUP can fill the length and detect when it's been connected to ground with no trouble. I never did get him to find the time to fill the wire though but it would be fun to see if 300 baud would be possible.

I've also seen several posts here where people were getting false digital signals due to long wires. It will depend on how electrically noisy the environment is and the wire (shielded, twisted pair, etc.). A stronger pull-up might be necessary or it might be possible to filter the spurious signals in software. I would also consider input protection:

I recommend normally closed switches that open on a push.

.

If you're in a place where big motors are in use or there are other EMF noise sources then yeah you need all that. The Hot Wheels guy isn't but he used CAT cable anyway which if you ground the shield eliminates the long wire problem.

It doesn't take much to find out what kind of environment you're in if you have an Arduino and even 30 cm of wire and the Arduino EMF detector sketch that Make shows on Youtube.

DVDdoug:
The simplest thing would be to get an Arduino Mega (54 I/O pins).

The "right way" is probably some multiplexer chips. (Sorry, I don't have a specific recommendation.) A multiplexer switches between inputs... For example, there is only one analog-to-digital converter inside the ATmega chip but there are multiple analog inputs and a multiplexer in the chip so your Arduino can have multiple analog inputs.
That can work but personally I hate using analog when everything is really digital (the switches are digital and the data is digital).

I am thinking that this is probably my best bet. I am going to do some research and see what I can come up with. Thanks for the help

'1284P, 32 IO pins
2560 (Mega), 70 IO pins - 0-53 are digital only, 54-69 are marked analog inputs 0-15

GoForSmoke:
It doesn't take much to find out what kind of environment you're in if you have an Arduino and even 30 cm of wire and the Arduino EMF detector sketch that Make shows on Youtube.

The environment will not be constant. You could run the test and find it's quiet, then, only after installing the whole thing, notice that turning on the blender brings out the poltergeists in your system.