I'm working on a project with a joystick and I'm trying to keep everything a simple and low latency as possible. I am reading the pots with the onboard 10bit ADC on the ATmega 32u4 but may be upgrading to either a 16bit ADC or 24 bit ADC. How can I filter noise out of the signals?
The Atmel ATmega328 datasheet, section 24.6.1, recommends that you drive the analog input pin with an output impedance of 10 KOhm or less. Also, it recommends that you remove high-frequency components with a low-pass filter. (That low-pass is sometimes called an antialiasing filter).
The simplest possible low-pass filter is a resistor and a capacitor.
+5V +5V | | (sensor)---resistor---+---(Arduino) | | | | capacitor | | | | GND----------------GND--------GND
Contrary to popular belief, it is not possible to make an antialiasing filter in software.
For an initial low-resolution prototype, a quick rule of thumb is to pick the RC time constant at least 10 times as long as the time between samples.
So if you are sampling at around 1000 Samples/second (i.e., a sampling interval of 1 millisecond), then 100 Ohms of resistance and (roughly) 100 uF ceramic capacitor may be adequate. (The RC time constant here is RC == 100 Ohms x 100 uF = 10 milliseconds).
Many joysticks already have a relatively high output impedance; you'll need to use a resistor with that much less resistance to compensate. (Sometimes you don't need any additional resistance; but you still need that capacitor between the Arduino analog input pin and the Arduino ground pin). (Many sensors have an output impedance more than 10 KOhm; people who use them are pretty much forced to use an op-amp chip to get clean signals).
Entire books have been written on signal filtering. In addition, there are many other techniques for getting higher resolution analog signals, higher speed data collection, and trading off between them -- but they are probably overkill for reading the position of a joystick.
One possible approach is to go for a completely software side solution.
Microsmooth is a signal processing library that I am working on that is specifically intended for low latency, low memory signal smoothing. It is still in development, but even now, most of the filters work in less than 100 microseconds per call while giving fairly good accuracy and smoothing. Also, the header file allows for simple configuration for certain filter parameters.