I'm trying to keep an Arduino project's code simple, which required resigning myself to the fact it won't be very robust as it decoded paper feed motor motion of a Canon Pixma MX340 multi-function inkjet. I'm at the mercy of a magic threshold value, and the errors it could introduce if it's too small or too large.

The Arduino sketch is looking at position reported by a quadrature encoder in this gearbox and, if it hasn't moved in 10 milliseconds (my magic threshold value), print how far it has moved since the last time it stopped someplace for at least 10ms. I've also added code to track the shortest time between encoder positions encountered during this interval, which reflects the fastest speed attained.

Before this threshold-triggered report, I would have a long list of numbers that I could import and plot in Excel. Here's the position & velocity graph for the machine's startup sequence.

And now, I have a very short list of movements taken and how fast it moved to get there. Here is the startup sequence again in the new format:

timestamp,count,min_us_enc
16,1799,28
13003168,2701,36
13478700,-1800,-28
13622500,-1800,-28
16468560,28020,36
20880704,2700,36
21135412,-2700,-38
21392592,-15000,-68
23213924,1800,28
25595052,-1799,-28
25739804,1798,28
25884356,-1798,-28

Timestamps don't line up between these two different presentations because they were taken on different sampling runs, but the change in encoder counts and velocity match. This is a far more concise report of motion control behavior, presenting information I wanted and discarding the rest.

One big difference between this output and the goals I had originally set is the lack of reporting on times when the system sat still. I thought it would be useful to know when nothing changed from time X to time Y, but the simple implementation generated noise from small movements and I didn't come up with an elegant way for it to coexist with my debounce code. I thought about it some more and remembered my goal here is to capture what kind of movements are involved in this gearbox. I don't really care about the times when it didn't move, so I deleted all associated code as unnecessary complexity.

We'll see if that turns out to be the right call or if I will regret not investing the effort to make it work. For now, this decision means a caveat on interpreting my decoded output: timestamps corresponding to each motion includes the time spent sitting still before each motion. Example: the third and forth lines of data both reflect a move of -1800 encoder counts...

13478700,-1800,-28
13622500,-1800,-28

The timestamps are only about 144 milliseconds apart, but looking on the big chart above we can see the actual movements are nearly 3 seconds apart. That's because the second timestamp here was actually the start of that ~3 second period of staying still, before moving another -1800 encoder counts.

Despite its flaws, I think it'll be useful enough of a tool to parse the motions I've been looking at.


This teardown ran far longer than I originally thought it would. Click here to rewind back to where this adventure started.

Captured CSV and Excel worksheets are included in the companion GitHub repository.