We’ve been really struggling this year with velocity noise on the REV Throughbore encoder. We have one on each side of our drive train (custom WCD), on the same shaft as the center traction wheel (corner omnis), with the quadrature output wired to the DIO on the rio. There’s no noticeable amount of backlash from the wheel to the encoder, and our drive motors are situated by the back wheels, so about 10+ inches away from the encoders. We’ve tried upping the samples averaged in the encoder class, but this doesn’t help as much as hoped.
Here’s similar data, but this time with the velocity calculated by dividing the change in reported encoder distance by the time measured since the last calculation. These spikes are mostly due to GC or some timing wackiness in Java, but similar spikes show up on occasion when running with low (<10) samples per average and higher speeds.
Note: All these tests were run with the robot disabled and the drive motors disconnected from the controllers, so EMI from motors seems an unlikely culprit.
We have no ferules on the encoder wires if that’s relevant, and there is about 15-25 degrees worth of wheel rotation in backlash from the axles to the motor output.
Any ideas on why it’s so noisy? We’ve been trying to do path following and the feedback controllers really don’t seem to play nicely with this data. I’ve considered getting the alternate encoder breakouts and just running the encoders to the motor controllers and running PID there, which might be better, but I have some concerns about this affecting our pose estimation with CAN delays and whether it would even help the problem.
What is the vertical scale in these plots? How fast is the shaft actually spinning? Velocity measurement on the Rio for quadrature type encoders works by measuring the length of the pulses. The sampling rate is 40 MHz, and the encoder has 2048 cycles per revolution. If we know how fast the shaft is actually spinning we can estimate how much noise is just due to the FPGA sample rate.
A couple of notes:
The default samples to average is 4, not 1
The last plot’s spikes are definitely due to Java timing jitter
Edit: as Joe Ross pointed out, with 4x encoding the FPGA is actually measuring time between any two edges, with 1x it’s measuring duration between the same edge on one of the signals.
Assuming 6" wheels (18.8" circumference), 1 meter/s (39.4 in/s) translates to 2.1 rev/sec, and thus ~4300 counts/sec. With 4x decoding, the time between any two edges should be ~58 us, so at a 40 MHz sample rate that’s ~2300 counts. Conversely, a 1 count difference will translate into a “noise” of 0.0004 m/s. So I think we can discount FPGA sampling as the reason for the noise you’re seeing.
It would be very interesting to hook this up to an oscilloscope to see what the pulse train looks like.
The problem may be a fundamental incompatibility between the sensor used in the throughbore encoder and the way the FPGA measures rate, at least with 4x decoding. The AEAT-8800 sensor datasheet has this concerning statement and figure:
With reference to the output period at A and B. The relative accuracy of the edges to each
other at a CPR setting of 256 is within ± 10% for 5V operation in a typical condition. Therefore, based on a period at A or B, the edge occurs in a window between 40% and 60% as shown in
the following figure.
I read this as meaning the pulse length may not be well controlled and could vary as much as +/-10%. This is not at all how optical encoders behave, and would almost certainly explain the noise you’re seeing. Definitely try 1x decoding, as doing so would change it to measuring rising-to-rising and might mitigate this particular oddity as well as decrease overall measurement noise.
Well, so much for that potential workaround… If the edge uncertainty applies more broadly, though, that could certainly explain the issue. We’d have to do some scope measurements to verify.
Unfortunately I don’t have a better workaround other than further increasing the sampling averaging. The FPGA (currently) does not support any other method of measuring velocity (e.g. counting number of edges over some interval of time).
If I can get my hands on an oscilloscope I’ll send the data but I don’t know of a way I can access one currently. Could connecting them to spark maxes and running control loops there fix the issue? I’d imagine the through bore was more designed with the intention of connecting to a spark than the rio. If I turn down the status frames from everything that I don’t really care about on CAN and max out those two I should be ok for using the encoders for odometry right?
Yeah we’re using that cable, A and B channels hooked up to the DIO in the RIO with the regular Encoder class from WPILIB. It goes straight from the encoder to the rio, no extensions, modifications, and I don’t think it should matter much since it’s a digital signal, but no ferrite beads or anything around the cables.
Note: I’m just dense and said ferrules instead of ferrite beads in the original post.
Is your encoder wiring bundled with any motor controller output wiring?
In 2018 and 2019 we had some flaky quadrature encoder counts that ended up being edges coupled into one or both phases from motor controller outputs in the same wire bundle. An inch of separation cured that problem.