5
\$\begingroup\$

I am developing a hardware system where an Arduino sits in the server room and communicates with the main computer via USB/serial. Users can push buttons at remote panels to trigger different functions on the computer.

The furthest remote panel is 250ft away, connected with Cat5e cable. Each panel has a total of 7 buttons, using each of the wires in the twisted pair with 1 left-over for ground.

I'm wiring each of the buttons directly to the Arduino, using the internal pull-up resistor. There seems to be a lot of consistency and reliability issues with this implementation. Sometimes the button presses don't register, and other times the other wire in the twisted pair will trigger instead (orange / orange white.)

How can I prevent this cross-talk and inconsistency?

\$\endgroup\$
2
  • 1
    \$\begingroup\$ debounce in software to avoid ghost false-positives. use stronger pullups to avoid ghost false-negatives. might also try small caps (0.1 - 10uf) on each input to gnd to avoid catching tiny impulses. If you only need to press one button at time, hook each to a different resistor value and gnd, then quadruple the wiring: 4 for gnd, 4 for signal. Pull up the signal at the Arduino end, so each button creates a unique voltage divider output, which is read by the ADC. Even with noise, you should be able to distinguish 7 unique values including 0 and 1023. tune pullup to compensate wire losses. \$\endgroup\$
    – dandavis
    Aug 19 at 21:00
  • 4
    \$\begingroup\$ Please draw a schematic (edit your question with the circuit tool) of what you have. \$\endgroup\$
    – Voltage Spike
    Aug 19 at 21:15
31
\$\begingroup\$

The point of the twisted pair is to have a signal and its return on the pair. Using the two halves of a pair for an unrelated signal is an unintended use, and the tight twist of the two halves together leads to severe crosstalk, as you've experienced.

Consider using a microcontroller at the remote end, and a differential signal such as RS-422, to communicate back to your local end. At lower speeds like 9600 bps (enough for 8 buttons) you shouldn't encounter issues from the mismatch between the common 120 ohm impedance for RS-422 and the 100-ohm impedance of the Ethernet cable.

The two differential legs of the signal line should be on the same twisted pair.

\$\endgroup\$
2
  • \$\begingroup\$ I was going to suggest RS-485 but that seems to be the exact same thing, just using tri-state outputs to make a bus? \$\endgroup\$
    – AndreKR
    Aug 22 at 15:30
  • \$\begingroup\$ @AndreKR, that's correct, RS485 is essentially a more capable specification that can share a single twisted pair with multiple nodes driving it at different times. I don't know enough about the original application in the question to know if a single RS485 bus is feasible; it looks like they may need a star topology based on the physical location of the panels and server room. \$\endgroup\$
    – nanofarad
    Aug 22 at 15:38
9
\$\begingroup\$

Since you probably don't need ultra snappy response to the buttons, I'd first try adding simple RC filters to the switch lines. Ideally on the microcontroller side but I think you'd still get benefit on the switch side. You're getting cross talk because when the switch triggers it snaps the line to ground with a sharp edge. That sharp edge has a lot of high frequency energy that couples into the adjacent wires. If you slow the edge down with a simple RC filter you should get much less cross talk and increase the immunity to noise in general (if you do it on the microcontroller side). Pick a cutoff frequency somewhere around 100 Hz (see the wiki link below).

schematic

simulate this circuit – Schematic created using CircuitLab

https://en.wikipedia.org/wiki/Low-pass_filter#RC_filter

\$\endgroup\$
1
  • \$\begingroup\$ I like this solution, no need to make it complicated if a resistor and cap will fix it. \$\endgroup\$
    – Drew
    Sep 13 at 23:23
6
\$\begingroup\$

As others have suggested, you may do some encoding on the far end, and transmit differential signals down the cat5e cable.

An alternative that relies upon this being a human interface, and consequently low data rate, is to use DTMF, the signaling method for land-line touch-tone telephones.

You can get a DTMF encoder for about $5 from reputable sources, and a multi-channel DTMF decoder for about the same. The UI buttons need to be arranged in a matrix, so that pushing one button connects two pins.

Some drawbacks include a small latency, and inability to signal multiple button pushes simultaneously.

Some advantages. Very low parts count. Easy debugging. High reliability. Because it is low frequency, termination need not be very precise.

This solution is only suitable for a system that does not require high data throughput such as yours.

\$\endgroup\$
1
  • 3
    \$\begingroup\$ The keys (pun intended) to this, which you may want to add to your answer, are that (a) this works just like telephone signaling over a single pair and (b) twisted pair Ethernet is well suited for telephone use - if you go back to Cat 3 days it was quite common to combine a phone line (or 2) with Ethernet (which only needed 2 pairs) in a single cable. \$\endgroup\$ Aug 20 at 15:28
4
\$\begingroup\$

You could also use a pair for power/ground to power three differential pair drivers (perhaps 3/4 of a AM26LS31) on the far side to make 7 possible combinations and have each switch transmit a unique binary digit to be decoded at the Arduino via a differential pair receiver with 100-ohm terminators. You'll have to do a little diode logic but the Vih of the AM26LS31 is 2V so that shouldn't be an issue.

\$\endgroup\$
4
\$\begingroup\$

Building on answers and comments that others have mentioned:

  1. The cross talk will be manageable if you have enough debounce. Say, 0.5 sec.
  2. The internal pullup is too high a resistance for that distance. I'd recommend a max of 1k for that distance.
  3. Also, at the arduino, make sure to use a ceramic capacitor at the input (0.1 uF) to take out interference.
  4. If there's too much noise for this, you could also use an optocoupler along with the software debounce, but I dont think you'll need it.

The debouncing may need some user training though, to get them adjusted to the 0.5 sec delay.

\$\endgroup\$
4
\$\begingroup\$

I had a somewhat similar issue about 4 years ago, sorta. I was running CANbus over about 250 ft of CAT5. Everything was running fine while the cable was coiled up in the box (the kind bulk cable comes in). At installation things went weird and the signal was becoming intermittent. That was solved by slowing the transmission speed down considerably. However this doesn't really solve your problem.

As others have indicated, you have two problems, the switch bounce, which by its very nature, is going to inductive coupling between adjacent wires (in this case the twisted pairs). You are using CAT5 in exactly the wrong way, but hey, CAT5 cable is cheap and easy.

I am assuming you want to avoid wiring up more components to your existing circuit, I get that, but I agree with other posters, 250' of cable back to your Arduino inputs is risking damage to your Arduino.

So that being said, debouncing the switches in software is the zero cost way to solve it. A simple delay will get mediocre results. There is a detailed write up by Ganssle here:http://www.ganssle.com/debouncing-pt2.htm There is an algorithm in C described here (worth reading): https://www.kennethkuhn.com/electronics/debounce.c Another guy had a similar problem as yours and found a fellow that implemented the code in a form easily implemented for an Arduino. His post is here: https://forum.arduino.cc/t/debouncing-many-switches-used-for-mcu-input-via-a-shift-register/489054/2 This guy goes into a lot of useful detail and provides links to the library on Github (https://github.com/tcleg/Button_Debouncer) where the programs are. It is robust, tweakable and you can adjust the code to multiplex buttons together, allowing you many more combinations than just you 7 buttons.

You will likely have to muck about a bit with the code, but it's pretty straight forward works well.

Going back to the other's suggestions of using an Arduino at both ends and using something such as RS-422 to transmit the signal, I can suggest these modules (which are RS-485. They are quite nice, RS-485 modules: https://www.droking.com/TTL-To-RS485-Module-DC-3.0V-30V-RS485-To-TTL-Mutual-Conversion-Hardware-Automatic-Flow-Control-Module-Converter-Module?search=rs485 cheap and you only need to use the serial pins on you Arduino, and using only one pair of wires. The are powered off the 5V and GND pins on the Arduino. They have a link to Amazon. These are nicer than the really cheap boards and RX-TX leds help debug.

\$\endgroup\$
3
\$\begingroup\$

250 feet and directly into an unprotected micro input? Ahh, might want to rethink that!

Microprocessor IO should nearly never be directly exposed to the outside world (I say nearly because there are some cases where it is hard to avoid).

Were I drawing this, I might keep your one button per wire thing that same (No real reason not to), but the doings at the processor would be more subtle.

Firstly, switches typically have a minimum as well as a maximum switching current if you want the things to work reliably, and I would bet that your 100uA or so from that built in pullup is nowhere close to being enough current.

Secondly, filtering at the input, it will help a lot.

This is about the minimum that I would use in that situation:

schematic

simulate this circuit – Schematic created using CircuitLab

R2 provides some real current to the switch contacts to provide the necessary whetting current to make them work reliably, adjust per the switch datasheet value.

R1 serves two purposes, it acts as a filter in combination with C1 to strip any RF off the line, a long wire is after all a perfectly cromulent aerial unless you take countermeasures, it also acts in combination with the diodes to limit the surge current that could flow dues to ESD or induced surges, and at least give the micro some sort of a chance.

It is not at all uncommon for the protection networks in industrial doings to add up to more parts then the rest of the system, but that is the price of robust design.

My favoured approach to this sort of thing is actually to use an analogue input, ONE pair of wires and switch series resistors at the remote end, do it right and the processor can detect short and open circuit cables as well as any combo of up to about 6 or so buttons, not bad for one pin and a small handful of passives. This trick is stolen directly from automotive practise where it is very common on things like steering wheel mounted controls.

schematic

simulate this circuit

This lets you detect any combo of the buttons as well as a shorted or open cable.

\$\endgroup\$
2
\$\begingroup\$

Connecting the microprocessor pins to the outside world is shaky at best. You need to use some sort of interface to clean up the signal and isolate the micro from the outside world. A simple voltage divider shown below will do the trick. Feed the switch with a higher voltage such as 12V if you have it. The top of the voltage divider goes to the button, the bottom is ground, connected to the ground that feeds the 12V to the switch. R1 is about 1.4K R2 is 1K the output goes to the micro pin. This circuit is reliable and inexpensive.

enter image description here

\$\endgroup\$

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.