[sdiy] Need goog working rotary encoder in C code..

Brian Willoughby brianw at audiobanshee.com
Sat Aug 7 09:49:07 CEST 2021

The Bourns PEC11L is rated for 60 RPM, maximum. That's 1 rev/sec or 50 ms/pulse:detent.

The contact bounce at 60 RPM is 10 ms, so that leaves only a small window in which to read the steady switch state before it changes again. A challenge here is that I would expect a pulse a.k.a. detent to involve all four transitions of the quadrature pattern. If that is correct, and each transition involves 10 ms of bounce, then you have a total of 40 ms of bounce during each 50 ms cycle, and that's only 2.5 ms of steady state in which to read each state.

The Bourns data sheet says "Devices are tested using standard noise reduction filters. For optimum performance, designers should use noise reduction filters in their circuits." I assume that this means a simple RC filter, but one which would not interfere with the 2.5 ms window. In other words, the RC filter should smooth out the contact bounce that occurs during the first 10 ms, without holding the voltage so long that the 2.5 ms window is not still outside the logic threshold to detect the change. You probably want to confirm the signal integrity with a 'scope if you're having trouble.

One technique that was mentioned in the thread is to use a counter. This allows the bounce to occur, with every high value adding 1 to the count and every low value subtracting 1. Thus, even if you read unfiltered bounces, the final value should still be correct. The trick here is to only count the changes, not every polled value (if I recall correctly).

Given these time frames, you must consider the clock rate of your PIC16F as well as the operating speed of your particular firmware implementation. If your code cannot process an entire pulse:detent in 12.5 ms, then you're probably going to read very unreliable values.

There are processors such as the TM4C ARM family from Texas Instrument that have quadrature encoder interface peripherals. With these, you can program the hardware for a maximum value and an minimum value, as well as control whether you want to allow the value to wrap around at the extents or stick at the extreme value. These peripherals handle the quadrature pins directly, and increment or decrement the current value based on the direction of rotation. There is even digital filtering available as an option. Unfortunately, these QEI peripherals still require proper pull-ups and filters, or they won't work reliably, either.

One question I have is whether typical users might exceed the 60 RPM in short bursts. I don't think anyone could twist a full 360 degrees at an excessive rate, but smaller rotation could actually be done faster than the rated maximum. I don't actually have any numbers here, but if I imagine what it would take to rotate an encoder a full turn at a constant speed during one second, I can easily imagine rotating it faster than that for a fraction of a full turn. In any case, if my estimate is correct, then you'll exceed to maximum rated speed of the hardware itself, regardless of your firmware.


p.s. Note that cheaper encoders have so much contact bounce that no firmware could possibly read them reliably. The only solution for cheap encoders is to train the operator to rotate the encoder VERY slowly.

On Aug 6, 2021, at 08:46, Jean-Pierre Desrochers <jpdesroc at oricom.ca> wrote:
> Hi everybody.
> I’m doing some tests on a rotary encoder and a PIC16F1783.
> A standard Bourns encoder like THIS .
> Connected using 2 x 10k pullups with 0.01uf caps to ground
> to PORTB of the micro. Interrupt calls (falling edges) used on encoder pins A & B.
> I struggled so far to get clean increments/decrements out of it.
> Many missing counts occur..
> I tried many source codes on the web with no luck..
> Is there anybody who’d have worked on this in the past
> and have a working c code ?
> No ARDIUNO please.
> Thanks !

More information about the Synth-diy mailing list