Better Pedometer - HELP NEEDED!

Posted on
Page
of 12
  • Here's 10 steps with the oxford filter. In my 3.10 version.
    Obviously 2 traces is not enough - but seeing how the different filters change the outout characteristic I realised the only way to normalise the code between different filters was to use PEAK detection.


    1 Attachment

    • oxford_walking.png
  • ideally I'd like to be able to run it over some data and say for sure that yes, it does do a better job.

    Can I beg you to implemnt the state machine as well in the firmware. It really is the only part of the algorithm that is accepting and rejecting real and false step sequences on every step at the moment. The current F/W implemenation does not do this well at all in my view. Its an essential part of the algorithm. If you look at the results I am getting with the javascript version - the improvement for non step counting is entirely down to the state machine. It may seem a bit more complex BUT I think the results prove its worth. It would potentailly mean you would have to change the STEP event to return X or 1 steps depending on if there had been a full pass through the state machine at the start of a sequence. But its a small price to pay in my opinion for a vastly improved step counter.

    There is still a lot more tweaking and testing work to be done. But if you move to the same approach I am using in 3.10 we will be aligned. I am considering building a test rig so I can feed recordings into my javascript version so I can do quick tests of different values of X in X and the raw threshold etc.

  • new recording. Sitting for 1hr with 2-3 getting up and moving to a different room. The AmizFit recorded 58 steps for this.


    1 Attachment

  • Thanks! Yes, I'll add it in.

    I guess from my point of view it seemed like it didn't matter whether it recorded two separate periods of stepping or not as long as it rejected steps that were on their own, but if you're finding that it really does make a difference in step rejection then yes it shouldn't be too hard to add.

    As far as the test rig goes - yes, you could build something with Node.js on the desktop very easily I imagine, then you could plough through the test data very quickly.

    However at some point if the approaches are aligned you could move to the test rig I'd already made for the C version? It's not that hard to compile and get working at all - if you had a raspberry Pi I imagine it would 'just work' out of the box.

  • Just a quick one - in your tests, is the minimum step threshold actually needed? It seems like the low pass filter will filter out any high frequency so you shouldn't even gets steps that are less than 0.3 sec apart?

    It's just one less variable that needs tweaking :)

  • Hi @Gordon - I recorded a 6hr accelog recording. When I attempted to download I got the following being dumped to the IDE console and the watch hung and stopped updating the watch app. Had to do a reset.

    ODg0LDQxOAoxMjc3OTQ2MCwyMDUwLC03OTAzLDM4MwoxMjc3OTU0MCwyMDQxLC03OTcyLDM3NQoxMjc3OTYyMCwyMDAzLC03OTc5LDM5NwoxMjc3OTcwMCwxOTU5LC03OTM5LDM5MAoxMjc3OTc4MCwxOTU1LC03OTYzLDM4NwoxMjc3OTg2MCwxOTU0LC04MDAwLDM5NAoxMjc3OTk0MCwxOTYyLC04MDQzLDM4OQoxMjc4MDAyMCwxOTgyLC04MDQ2LDM2OQoxMjc4MDEwMCwxOTc1LC04MDMwLDM2OQoxMjc4MDE4MCwxOTU0LC04MDQ5LDM2MQoxMjc4MDI2MCwxOTg4LC04MDQ5LDM3MwoxMjc4MDM0MCwyMDM3LC03OTk4LDQyMgoxMjc4MDQyMCwyMDE4LC03OTQ4LDQxOQoxMjc4MDUwMCwxOTkyLC03ODgyLDQzNQoxMjc4MDU4MCwyMDE0LC03ODYwLDQ1MQoxMjc4MDY2MCwyMDQxLC03
    OTE4LDQ1MAoxMjc4MDc0MCwyMDcxLC03OTQ1LDQ0OQoxMjc4MDgyMCwyMDc2LC03OTkyLDM4MQoxMjc4MDkwMCwyMDYxLC03OTc5LDM2NgoxMjc4MDk4MCwxOTk1LC03OTMxLDQxMAoxMjc4MTA2MCwxOTU1LC03OTQzLDQ5MAoxMjc4MTE0MCwyMDA1LC03OTQ4LDUxOQoxMjc4MTIyMCwyMDExLC03OTQyLDQ1NgoxMjc4MTMwMCwxOTcyLC03OTM5LDQxOAoxMjc4MTM4MCwyMDEzLC03OTIxLDQzNQoxMjc4MTQ2MCwyMDQwLC03OTAzLDQ2OAoxMjc4MTU0MCwyMDE5LC03OTU1LDQ1OAoxMjc4MTYyMCwyMDI3LC04MDA1LDQyNwoxMjc4MTcwMCwyMDA0LC04MDAzLDQyMQoxMjc4MTc4MCwyMDIwLC04MDEwLDQxMAoxMjc4MTg2MCwyMDUyLC04MDA1LDM3MQoxMjc4MTk0MCwyMDA3LC03
    OTc3LDQxMgoxMjc4MjAyMCwxOTk1LC03OTgxLDQ4MwoxMjc4MjEwMCwyMDA3LC03OTc0LDQ5OQoxMjc4MjE4MCwxOTY5LC03OTcxLDQ1NQoxMjc4MjI2MCwxOTYwLC03OTk1LDQyNgoxMjc4MjM0MCwxOTgyLC03OTk4LDQ1NQoxMjc4MjQyMCwxOTkyLC03OTgyLDQ2MAoxMjc4MjUwMCwxOTc5LC03OTQxLDQzNwoxMjc4MjU4MCwxOTc0LC03OTQ3LDQxOAoxMjc4MjY2MCwxOTYyLC03OTU4LDM5MQoxMjc4Mjc0MCwxOTY2LC03OTM4LDQwNQoxMjc4MjgyMCwxOTQyLC03OTM3LDQ4MAoxMjc4MjkwMCwxOTM5LC03OTIwLDUzMQoxMjc4Mjk4MCwxOTk4LC03OTM3LDU0NwoxMjc4MzA2MCwxOTk5LC03OTgwLDU0NgoxMjc4MzE0MCwyMDA5LC03OTc0LDQ5NAoxMjc4MzIyMCwyMDMwLC03
    OTcxLDQ1MgoxMjc4MzMwMCwyMDE0LC03OTYxLDQwOAoxMjc4MzM4MCwxOTkwLC03OTU2LDM2MQoxMjc4MzQ2MCwxOTk2LC03OTgwLDM5MQoxMjc4MzU0MCwyMDA3LC03OTc0LDQxMwoxMjc4MzYyMCwyMDM4LC03OTYzLDQwNwoxMjc4MzcwMCwyMDY5LC04MDAwLDQwMwoxMjc4Mzc4MCwyMDc1LC04MDE3LDQ0NQoxMjc4Mzg2MCwyMDQ0LC03OTc0LDQ5MAoxMjc4Mzk0MCwxOTc4LC03OTU0LDQ2OAoxMjc4NDAyMCwxOTczLC03OTYyLDQwNgoxMjc4NDEwMCwyMDA1LC03OTU3LDM4NgoxMjc4NDE4MCwyMDI5LC03OTcyLDM4NQoxMjc4NDI2MCwxOTk3LC03OTYxLDQyOAoxMjc4NDM0MCwxOTgyLC03OTY1LDQyMgoxMjc4NDQxOSwyMDA5LC03OTg0LDQxOQoxMjc4NDQ5OSwyMDIyLC03
    OTI1LDQ0NAoxMjc4NDU3OSwyMDExLC03ODk3LDQyMQoxMjc4NDY1OSwyMDA2LC03OTEwLDQyNwoxMjc4NDczOSwxOTk1LC03OTMzLDQzMAoxMjc4NDgxOSwyMDA3LC04MDAzLDQ0MAoxMjc4NDg5OSwyMDI5LC04MDI3LDQ0NAoxMjc4NDk3OSwxOTk3LC04MDA1LDQzOAoxMjc4NTA1OSwxOTY1LC03OTg1LDQyNwoxMjc4NTEzOSwxOTU4LC03OTc2LDM3OQoxMjc4NTIxOSwxOTU1LC04MDA2LDM2NQoxMjc4NTI5OSwxOTg4LC04MDAzLDQxOAoxMjc4NTM3OSwyMDIxLC04MDAyLDM5MgoxMjc4NTQ1OSwxOTg0LC04MDM1LDMyMAoxMjc4NTUzOSwxOTg1LC03OTkxLDI4NgoxMjc4NTYxOSwyMDI4LC03OTU0LDM1NgoxMjc4NTY5OSwxOTk2LC03OTcwLDQ4MgoxMjc4NTc3OSwxOTgyLC03
    OTc4LDQ1NgoxMjc4NTg1OSwyMDUyLC03OTU2LDQxOAoxMjc4NTkzOSwyMDY3LC03OTM3LDQ3NwoxMjc4NjAxOSwyMDE0LC03OTYyLDUwNQoxMjc4NjA5OSwxOTY0LC04MDAwLDQ2NwoxMjc4NjE3OSwxOTQxLC04MDAwLDQzMQoxMjc4NjI1OSwxOTU2LC03OTg0LDQxNQoxMjc4NjMzOSwxOTYyLC03OTkzLDQwNwoxMjc4NjQxOSwxOTQ5LC03OTgwLDQyOQoxMjc4NjQ5OSwxOTY4LC03OTU3LDQzMQoxMjc4NjU3OSwxOTc3LC03OTQ2LDQ0MAoxMjc4NjY1OSwxOTk4LC03OTY3LDQzNgoxMjc4NjczOSwxOTkxLC03OTkzLDQwOQoxMjc4NjgxOSwxOTM2LC03OTgwLDQ3MwoxMjc4Njg5OSwxOTM3LC03OTQ4LDUxMQoxMjc4Njk3OSwxOTU0LC03OTE3LDQ1MgoxMjc4NzA1OSwxOTUzLC03
    OTI3LDQyNQoxMjc4NzEzOSwxOTcwLC03OTgzLDQwMwoxMjc4NzIxOSwyMDEyLC04MDE4LDQxOQoxMjc4NzI5OSwyMDA2LC04MDE3LDQwOQoxMjc4NzM3OSwxOTk1LC04MDA5LDM4OAoxMjc4NzQ1OSwyMDA3LC04MDEzLDQyMAoxMjc4NzUzOSwyMDIxLC03OTY0LDQ0NAoxMjc4NzY5OSwyMDYxLC03OTQxLDQ0MgoxMjc4Nzg1OSwxOTg4LC04MDA3LDM5NAoxMjc4NzkzOSwxOTk1LC03OTUzLDQ1NwoxMjc4ODAxOSwxOTk4LC03OTM2LDQ4NwoxMjc4ODA5OSwyMDE3LC03OTE5LDQ2NgoxMjc4ODE3OSwyMDA4LC03OTQ1LDQwNgoxMjc4ODI1OSwyMDA0LC04MDAwLDM4NgoxMjc4ODMzOSwyMDExLC04MDE4LDM1OQoxMjc4ODQxOSwyMDE0LC04MDE3LDMzMAoxMjc4ODQ5OSwyMDMzLC04
    
  • Assume you are referring to the min time threshold of 333ms for a step in the state machine. Good question. Yes its needed. In theory it should not be needed but we dont have a perfect filter and a perfect sampling rate. I have seen the lower threshold reject false steps when driving and other occasions. I have done a lot of watching of the debug output I print to the console so have a good feel for what is going on now. We could take it out and do test runs through the recorded data to see the impact. At the moment I dont think it is causing any harm or a major source of error.

    One thing I am wondering if we need a different format for the recorder. The recorder logs the x,y,z componants - but in the code we use the m value which is calculated by the firmware. To eliminate another potential difference / source of error - I think we should record time and m only.

  • I have a linux setup on my chromebook so I could setup the C version. I will do that once I feel I have got to the end of testing / loggng. I will also setup the Node.js as well.

  • Argh, shame about the download. Are you using the online IDE, or the 'native' one? In the past I know we had a problem with timeouts on long downloads, but I thought that was fixed now.

    What if you download using the app loader itself? Connect to your watch, go to 'my apps' and then click the upload button next to the app.

    Thanks for the info about the threshold...

    In terms of the logging - working out magnitude from the data is pretty easy and is also easy for us to test. While it's less data to log (we don't even really need to log the timestamp), part of me was thinking that at some point we may need to look at the orientation of the watch to filter out certain types of unwanted step - and in that case we wouldn't want to have to re-record any data!

  • Ok, I've just converted this to C and pushed updated code.

    Running it with the csv file I gave shows interesting stats though:

    // a1bc34f9a9f5c54b9d68c3c26e973dba195e2105   HughB-walk-1834.csv  1446
    // oxford filter                                                   1584
    // peak detection                                                  1752
    // state machine                                                   1751
    

    So during walking, not much difference in the state machine, but it will hopefully manage to reject more non-walking steps as you say.

  • Assume line 1 - is original code / filter.
    As this is actual walking data - I would not expect the state machine to have to do much work or show much difference for that dataset. When I collected this data I tend to walk fairly quickly the 1 mile walk or so. I think there will be big difference when you run against the non walking recordings.

    1) driving log 0 steps in 36 minutes
    2) driving log 0 steps in 29 minutes

    Its the driving that is the weakest part now. I suspect tweaking things to get these to 0 will massively reduce the accuracy of when counting actual steps.

    Here are the things I think can be tweaked.
    1) X steps in X seconds could be 5 or 6 or 7 - after 7 I think it starts to work against accuracy
    2) The Raw threshold to gate the output of the filter, Currently +-10. Can go higher.
    3) The time we want the raw signal to be over or under threshold before we open / close the gate.


    2 Attachments

  • Why there need to be a threshold on the raw M input

    Place the watch on a table and you will still see some raw m signal from the accelerometer:

    523593,6,0
    523673,4,0
    523754,4,0
    523833,6,0
    523913,6,0
    523993,8,0
    524073,9,0 PEAK
    524153,6,0
    524233,5,0
    524357,5,0
    524393,4,0
    524473,5,0
    524553,6,0
    524633,7,0
    524713,7,0
    524793,8,0 PEAK
    524873,7,0
    524953,6,0
    525033,8,0 PEAK
    525113,5,0
    525193,2,0
    

    This signal has PEAKs. When using PEAK detection it means that the step state machine will get called from very small movements - EG when sat on a sofa.

    I have flashed 2.10.13 and am testing against 3.11.
    15 mins sat on the sofa the FW has done 13 steps and 3.11 has done 6 steps.
    The difference is that the FW has no minimum raw threshold that must be reached before
    we take the filter output.

    3.11 has this bit of code :

    
      if (raw_clipped > RAW_THRESHOLD || raw_clipped < -1*RAW_THRESHOLD) {
        if (active_sample_count < N_ACTIVE_SAMPLES)
          active_sample_count++;
        if (active_sample_count == N_ACTIVE_SAMPLES)
          gate_open = true;
      } else {
        if (active_sample_count > 0)
          active_sample_count--;
        if (active_sample_count == 0)
          gate_open = false;
      }
    
      if (!gate_open)
        accFiltered = 0;
    
    
    

    What this code is doing is saying is the raw m value bigger than room noise for more than 3 samples.
    The raw threshold is set to +-10. And to take the filter output the ABS(input) must be greater than the threshold (10) for about 1/4 of a second. This is necessary otherwise PEAKs in the chip noise or noise from the ground get passed into the state machine. We want to definitely moving before we start calling the state machine.

    I'm convinced this concept is needed AND it can also be one of the parameters we use to TUNE the step counter against the accellog recordings.

  • Thanks for all that extra data! I just added it to the step-count repo.

    Thanks, I'd missed the threshold in your code. I've now implemented it but as far as I can see it made no difference whatsoever to the steps recorded using your 3 data files. I guess maybe the threshold needs to be higher.

    ... but again, this is why it's really good to be able to run the code in a test harness

    However, I feel that what you've basically got there is a threshold? Before using the peak detector, we had the threshold on the filtered data - and personally I feel like it would be a lot cleaner to do the threshold after the filter.

    As is, when gate_open becomes true, accFiltered is now suddely>0 and all it takes is for the next sample after that to be lower and you've now got a step recorded.

  • but again, this is why it's really good to be able to run the code in a test harness

    Totally agree. Once we have all the necessary logs and agreed algorithm, identified parameters that we tune against the data - this will be the only practical way to run the 100+ tests that might be required to optimise the 2-4 tuning parameters. I have installed Node.js / npm but I have no Node.js experience - so its going to take a while for me to convert my code to a test harness. Going to focus on getting good recordings for a bit longer. Plus track the firmware updates you are doing.

    SLEEP TEST RESULTS
    Amiz GTS 2 - 10
    2.10.13 - 191 ** this is the extra steps coming in due to noise on the input
    3.10 App - 169

    As is, when gate_open becomes true, accFiltered is now suddely>0 and all it takes is
    for the next sample after that to be lower and you've now got a step recorded.

    No this is not the case.
    The raw threshold works like this.

    Count up to 3 consecutive ABS(raw) values that are over threshold - then open the gate
    Now we have readings that are not noise and represent actual movement
    The gate only turns off if active_sample_count-- counts down to 0 and it will take 3 consecutive out of threshold values for it to count down. This avoids the potential for counting steps when at rest.

    The gate opens up quickly when there is real movement, stays open and closes down quickly when the movement stops.

    The M of the accelerometer when the watch is at rest/stationary is biased in the 3-8 range.
    As per the screenshot above. The noise is not balanced across the zero line which is what I
    would have expected. I have thought of building that into the threshold code. Too early to tell.

    personally I feel like it would be a lot cleaner to do the threshold after the filter.

    Ideally I would agree but the amplication of the filter is not linear and very dependant on what gets through. With the 2.9.90 filter any input got heavily amplified. Also with a 12.5Hz sampling frequency we can only have a filter that works up to 6.25Hz - this introduces distortations and
    errors etc.

    The only way we could prove lineararity would be through mass tests and to try and get a set of real world recordings that had a range of increasing raw values in the output. The driving recordings are the most interesting for this. Using the theoretical response is not going to help when in the real world the signal has got low level noise and bumps in the round etc.

  • No this is not the case.

    I'm not entirely sure you got my point about this. You set up peak after accFiltered=0, so
    when gate_open=true, peak is full of zeros and if the next sample is less than the first you get something like 0,20,19 in peak and that is enough to register as a step.

    If you got rid of if (!gate_open) accFiltered = 0; and instead just had gate_open && peak[1] > peak[0] && peak[1] > peak[2] && accFiltered > stepCounterThreshold you wouldn't have the issue.

    JS test harness would be good, but I guess if we have all the data, we already have a working test harness in https://github.com/gfwilliams/step-count that uses the actual C code from Bangle.js, so long-term it feels safer to use than than to maintain two different step counters - one in JS and one in C

  • I'm not entirely sure you got my point

    Yes apologies, I realised a few hours later this is what you mean't.

    Good point, probably wont matter as we have the state machine to get through, but that assumes the state machine has timed out. But I agree its one less false PEAK and logically better.

    so long-term it feels safer to use than than to maintain two different step counters

    Yes I agree. The javascript stepcounter app was only to allow quick prototype of ideas etc.
    Its close to having served its purpose now.

    Uploading a log of 1 hour working at a desk. 0 Steps recorded on the AmizFit GTS2.

    Have just cloned the step counter test harness repository and ran it successfully.

    Done a lot of experiments and arrived at 8 steps in 8, gated entry to the state machine based on a raw threshold of 17 and no threshold at all on the filter output. This works really well. I did a test with the gating removed first and the difference on counting non steps was in the 1000s.
    I then wondered what the impact of having no threshold on the filter would be and the impact was positive.

    Latest test run below.
    github.com/gfwilliams/step-count

    File, Expected, Simulated, Diff, (Orignal)
    HughB-walk-1834.csv, 1834, 1754, -80, (1093)
    HughB-walk-2331.csv, 2331, 2143, -188, (1874) I actually got 2195 on the JS version (3.12)
    HughB-driving-36min.csv, 0, 13, 13, (1199) - lowest I have got it with no impact on walking
    HughB-driving-29min.csv, 0, 46, 46, (1153) - lowest I have got it with no impact on walking
    HughB-working-1h.csv, 0, 0, 0, (760)
    TOTAL DIFFERENCE 469

    Have done a couple of pull requests to the step-count test harness AND the Espruino repositories.

    I think we now have a pedometer that works !
    Will do some more logs soon.


    1 Attachment

  • That's great news, thanks for all your work on this! That's really exciting!

  • Added 2 more logs, updated harness, done pull request.

  • Ok - so I think in practice the Test Harness results are a bit on the optimistic side.
    Just added a couple of recordings and logged what the Javascript version recorded.

    Does the M value come from the chip or is it calculated by the firmware ?

    gcc -std=c99 main.c -o main
    github.com/gfwilliams/step-count
    X_STEPS = 8, RAW_THRESHOLD = 17
    File, Expected, Simulated, Diff, (Orignal)
    HughB-walk-1834.csv, 1834, 1754, -80, (1093)
    HughB-walk-2331.csv, 2331, 2143, -188, (1874)
    HughB-walking-2350.csv, 2350, 2198, -152, (1042)
    HughB-walk-6605.csv, 6605, 6012, -593, (3223) // actual 3.12 => 5261 ie -1344 under
    HughB-driving-36min.csv, 0, 13, 13, (1199)
    HughB-driving-29min.csv, 0, 46, 46, (1153)
    HughB-driving-18.csv, 18, 78, 60, (580) // actual 3.12 => 9
    HughB-working-1h.csv, 0, 0, 0, (760)
    Hughb-work-66.csv, 66, 56, -10, (980)
    HughB-mixed-390.csv, 390, 356, -34, (1871)
    TOTAL DIFFERENCE 1455

  • I did some actual realworld tests and came to the conclusion that the test harness results are not matching what you would get in a real world physical test. However the situation is complicated. In order to investigate will need to record the steps according to the AmizFit and also the current version of the step counter running on the bangle. Then compare with what the test harness gives.

    My final conclusions about what is working are based on real world tests rather than the test harness results. Our users will only every test this way.

    8 steps and 17 as the Thresold turned out to be too hard = it reduced the impact on DRIVING but at the expense of the accuracy of real world walking.

    • 15min Driving: Amix 19, Bangle 9 (test harness predicted 80 if I recall).
    • Walking Amiz 6605, Bangle 3.12 5261, 79% - bad result.

    Tried v3.13: 6 Steps / Threshold of 14.

    SLEEP Amiz 0, 3.13 65
    DRIVE Amiz 60 3.13 90 -- most of this was the first 400m. ** (see note below)
    WALKING Amiz 3191 v3.13 3158 -- 98.8%
    DRIVING Amiz 3, v3.13 = 78

    More real world test cases required BUT Here is my justification for the pay offs between
    X in X and the RAW threshold:

    This is what we ideally want in terms of behaviour from our pedometer:
    SLEEP: Less than 100 steps - this loses 1% of in 10K steps - ACHEIVED
    SOFA/DESK work - 0 steps or very low. - ACHEIVED
    DRIVING - Ideally no more that 100 steps per hour - Not really acheived
    WALKING - We want 98-100% accuracy - ACHIEVED - need more results

    Lets consider a typical day to consist of:
    SLEEP, DRIVE, WORK, WALKING - if the driving is a commute it may be 100-200s per leg of journey. With a return journey you could rack up 400 steps DRIVING in the day. But not
    everyone drives everyday.

    ** HOWEVER - I have observed that DRIVING is very non deterministic even with the AmixFit. The
    same drive one day will record 0 steps, the next day it will record 60 steps. The different
    bumps in the road, traffic conditions, etc produce a unique journey as far as the Accelerometer
    data is concerned.

    My final push on the firmware repro will be to set X=6 and RAW_THRESHOLD=14.
    I have these set on v3.13 on my bangles and will continue some tests.

    Future Work
    -Gather a good solid test of test results. EG 5 measures of the SLEEP, DRIVE, WORK, WALK so that we can be confident we dont just have one off results.
    -Investigate / Meaure how accurate the test harness is based measurements in the real world
    -Gather more / longer accellogs of different mixed activies (but with timeslines of activities).
    -Ask others to repeat some tests aginst FitBits and other smart watches if they have them.

  • Ok, great. I'm not quite sure what you mean by the M value? Acceleration magnitude?

    You can check in the code but the calculations to get that from x,y,z are done in the Bangle and are super simple. We should really be doing the same stuff in the test harness

  • M value? Acceleration magnitude?

    Yes Magnitude.

    We should really be doing the same stuff in the test harness.

    Yes - need to be the same so we can do predicatble modelling that will match the real world measures when actually walking with the device etc.

    I was not sure if the accelerometer chip does the calculation for magnitude OR the firmware does it. In the test harness I can see the In32_sqrt() function. Is this the same in the Bangle firmware. Was not sure where to look in the code.

    Found this in ./libs/banglejs/jswrap_bangle.c

    JsVar *jswrap_banglejs_getAccel() {
      JsVar *o = jsvNewObject();
      if (o) {
        jsvObjectSetChildAndUnLock(o, "x", jsvNewFromFloat(acc.x/8192.0));
        jsvObjectSetChildAndUnLock(o, "y", jsvNewFromFloat(acc.y/8192.0));
        jsvObjectSetChildAndUnLock(o, "z", jsvNewFromFloat(acc.z/8192.0));
        jsvObjectSetChildAndUnLock(o, "mag", jsvNewFromFloat(sqrt(accMagSquared)/8192.0));
        jsvObjectSetChildAndUnLock(o, "diff", jsvNewFromFloat(sqrt(accdiff)/8192.0));
      }
      return o;
    }
    

    Found this in
    ./targetlibs/nrf5x_15/external/micro-ecc/curve-specific.inc

    static void mod_sqrt_default(uECC_word_t *a, uECC_Curve curve) {
      ...
    }
    

    Not really sure how this compares to:
    Espruino/libs/misc/stepcount.c

    
    // quick integer square root
    // https://stackoverflow.com/questions/31117497/fastest-integer-square-root-in-the-least-amount-of-instructions
    unsigned short int int_sqrt32(unsigned int x) {
      unsigned short int res=0;
      unsigned short int add= 0x8000;
      int i;
      for(i=0;i<16;i++) {
        unsigned short int temp=res | add;
        unsigned int g2=temp*temp;
        if (x>=g2)
          res=temp;
        add>>=1;
      }
      return res;
    }
    

    Apologies I think * is confusing the code formatter

  • I think you're using 4 backticks where you only need 3, which is what messes with the formatter.

    The micro ECC one isn't related. What happens is:

    newSteps = stepcount_new(accMagSquared); at https://github.com/espruino/Espruino/blob/fc2d816c57bd36da89972aa39775ba03c3d591a5/libs/banglejs/jswrap_bangle.c#L1099

    and accMagSquared = acc.x*acc.x + acc.y*acc.y + acc.z*acc.z; where the acceleration values are the raw ones from the sensor, where 1g = 8192

    The test harness should be the same: https://github.com/gfwilliams/step-count/blob/master/main.c#L77-L87

    The int32_sqrt is defined inside stepcount.c: https://github.com/espruino/Espruino/blob/fc2d816c57bd36da89972aa39775ba03c3d591a5/libs/misc/stepcount.c#L156

    so it should be identical between calls

  • Thanks for that. The test harness is basically using the same code that the step counter is using ? So I was scratching my head and realised that my javascript version does

    function onAccel(a) {
      var m = a.mag;
    

    Hence wondering if a.mag comes from the accelerometer chip or its calculated in the firmware ?

  • Post a reply
    • Bold
    • Italics
    • Link
    • Image
    • List
    • Quote
    • code
    • Preview
About

Better Pedometer - HELP NEEDED!

Posted by Avatar for Gordon @Gordon

Actions