Issue with stroke detection in old-school mechanical FlyWheel #10
-
Hi Lars, I was able to hook up my rower to the Raspberry Pi and OpenRowingMonitor. I have the idea that stroke detection is off somehow as when I rowed 25 strokes, the monitor said over a 100. It also isn't consistent: sometimes it adds just one during a stroke, sometimes four. I recorded the data and pasted into Excel. The raw datagraphs are showing nice clean breaks. In the excel added some backward-oriented hysteresis to the raw data (i.e. absolute minimum and maximum values, as well as an maximum change of 25% with respect to the average of the last two accepted measurements), and the data looks pretty clean to me. I did correctly set up the number of magnets (there are four!) and I set the "liquidFlywheel" to false. To aid your analysis, I add the raw simulation file of the four runs I had, each run has 25 strokes, as well as the processed version in csv, and the resulting data from syslog in debug-mode for the third session. To be complete, I also add the RowingEngine.js. As GitHub doesn't allow me to upload .js and .csv files, I renamed them to a .txt. RowingEngine.txt |
Beta Was this translation helpful? Give feedback.
Replies: 3 comments 2 replies
-
Hi Lars, Compliments for the high quality of coding, and that is from somebody who reviewed code for decades as a professional. I could simulate the algorithm with real data and see where it went off the rails. I'll attach the Excel that helped me understand what was going wrong. I think I found the cause of the issue: it is in the core of the stroke detection. In essence: your approach for stroke detection is sound from a mathematical perspective, but it has the tendency to fail on the higher rotating air-resistance rowers, especially the ones with more magnets. What happens is that the continuous differentiation, based on currentDt (basically Delta Time), which you translate to Angular Velocity. I'm not certain how omegaVector (angle speed) and omegaDotVector are related, my gut tells me that that is the Angular Acceleration (and not Angular Velocity already). Anyhow, because of the Delta of the omegaVector, this enlarges any measurement errors as frequent measurement also brings subsequent measurements closer together (i.e. the wheel has not time to accelerate/decelerate that much). So basically you are substracting data that is pretty close together, which leaves you a lot of measurement error (see "Fifth 25 Strokes RAW" in my Excel). As the measurement speed is so high, chances of getting measurement errors are also bigger and also that they are significant (as the numbers are smaller). By the repeated differentiation, you mathematically end up with a constant and the measurement errors take over. When I looked at the data, my idea is that looking at the OmegaVector should work: the splits are easily identifyable. So what I did to fix stroke detection:
Based on my Excel file, it seems to work: I played with it, you need the hysteresis to make this work (flattening noise at the source) and the flank detection can't be less rigid. See "5th 25 Strokes w hyst, Velocity". |
Beta Was this translation helpful? Give feedback.
-
I implemented/hacked something to simulate the behavior of my Excel file. I ran all my files, and this approach handles it much better. I hope you see some inspiration to improve the code. |
Beta Was this translation helpful? Give feedback.
-
Hi Lars, A first solution with decent code and "some" parameters that can be tuned to the machine. I placed the really changed code it in the modified code in the "liquidFlywheel = false" part, as I can't test whether it can be tuned to a waterrower. First step is the sanity check of the recently gathered currentDt. By simply doing some sanity checks, I was able to reduce the false strokes with 50%. Given the machine it could be less effective, but putting some sane values in there does help. First check is a hard range check (upper and lower), second is a sanity check based on the procentual change with respect to the previous points. When the machine has less datapoints, this can be eased quite far. Second step is the Phase detection. The main concept op the Phase-detection is that everything on the rower is fixed enough that I can only need to care about time: based on change of the intervals between magnets you can decide whether the wheel is accelerating or decelerating. I feed that flank-detection in a mini-state machine which decides if a Phase can be changed. Here some parameters can be modified as well:
I hope this works for you too! |
Beta Was this translation helpful? Give feedback.
Hi Lars,
A first solution with decent code and "some" parameters that can be tuned to the machine. I placed the really changed code it in the modified code in the "liquidFlywheel = false" part, as I can't test whether it can be tuned to a waterrower.
First step is the sanity check of the recently gathered currentDt. By simply doing some sanity checks, I was able to reduce the false strokes with 50%. Given the machine it could be less effective, but putting some sane values in there does help. First check is a hard range check (upper and lower), second is a sanity check based on the procentual change with respect to the previous points. When the machine has less datapoints, this can be eas…