unsigned long RotaryEncoder::getRPM()
{
// calculate max of difference in time between last position changes or last change and now.
unsigned long timeBetweenLastPositions = _positionExtTime - _positionExtTimePrev;
unsigned long timeToLastPosition = millis() - _positionExtTime;
unsigned long t = max(timeBetweenLastPositions, timeToLastPosition);
return 60000.0 / ((float)(t * 20));
}
I am struggling with this function from a library to produce accurate RPM measurements.
Can someone explain it. Should the 20 be changed to a pulse count?
RPM is defined as rotations / time and then scaled to minutes
So RPM = rotations * 60000 / time (in millis)
Looking at the code it only uses a time variable and no rotations variable (or equivalent).
Conclusion: code is specific for an (undefined) encoder.
The number (20) represents the pulses per rotation.
Example:
if one knows that a certain rotary encoder has e.g. 100 pulses per rotation
And if one knows the time between 2 pulses is e.g. 12 milliseconds
The latter sentence means the RE made 1/100 of a rotation in 12 milliseconds.
In a second that would be ~83.33 x as much so 83.33/100 rotation in 1000 milliseconds.
In a minute that would be 60 * 83.33/100 == ~50 RPM.
In formula this is RPM = 60000 / (time * Pulse/Rotation)
I do not yet understand why the code uses the line with "max(two times)" as it should always be timeBetweenLastPositions.
So if your rotary encoder uses e.g. 64 pulses per rotation change the line in the library.
(should be a parameter to be configured to be portable).
My encoder uses 1024 PPR. So on my rotation count i divide the "ticks" by 2048 and I get an accurate reading. I assume that it is gettign 1024 "ticks" per interupt pin thus the 2048.
I had changed the function from 20 to 2048 and it was giving me crazy numbers. I wonder it I tried it at 1024 how it would respond. I will test.
I have looked at the max also and again cant say I 100% understand it. I may be able to put a PR/Issue on the git and see if he would explain his thoughts.