How to save correct data in FIT-Field?

Former Member
Former Member

Hi!

I'm new to programming in Monkey C. I wanna write a programm, which gets all the reading of the accelerometer and the magnetometer and saves it in a FIT-File.

Getting the data over Sensor.Info and saving it in an array is no problem. I was printing out the arrays in the console in Eclipse and they make perfekt sense. But when I save those arrays in a FIT-Field using the setData()-function, suddenly there are different, wrong values in the FIT-Field. (I use the Fit SDK to convert the FIT-Files to a CSV-File and import the File in Excel). I really don't know where my mistake is. I hope you can help me.

This is how I create the FIT-Fields:

When the user presses a button I start a timer which calls this function every 125ms:


Those are the printed values from the console:
XAccel: [654, 654, 654, 654, 654, 654, 654, 475]
YAccel: [476, 476, 476, 476, 476, 476, 476, 655]
ZAccel: [-586, -586, -586, -586, -586, -586, -586, -586]
Pitch: [0.496728, 0.496728, 0.496728, 0.496728, 0.496728, 0.496728, 0.496728, 0.715031]
Roll: [-2.301411, -2.301411, -2.301411, -2.301411, -2.301411, -2.301411, -2.301411, -2.460433]
XMag: [-118, -118, -118, -118, -118, -118, -118, -86]
YMag: [-86, -86, -86, -86, -86, -86, -86, -118]
ZMag: [202, 202, 202, 202, 202, 202, 202, 202]

Those are the values from my FIT-Fields:
X_Accel_Values: -1|-1|-1|-8388737|-8388737|-8388737|-8388737|-129
Y_Accel_Values: -1|-1|-1|-1|-1|-1|-1|68095
Z_Accel_Values: -256|16777215|2147483647|65407|-1|402653439|250657|0     //Interesting here: Third number is max. Integer
Pitch_Values: 4.2351647E-22|0.0|1.17549435E-38|0.0|0.0|0.0|0.0|0.0
Roll_Values: 0.0|0.0|0.0|0.0|0.0|0.0|0.0|0.0
X_Mag_Values: 0|0|0|0|0|0|0|0
Y_Mag_Values:0|0|0|0|0|0|0|0
Z_Mag_Values: -872415232|-1015597533|41205445|268435456|17195260|0|-553648128|91537093

Does anyone know why the values are different and how to fix it? Any Help is appreciated

Thanks!
Tim

  • Check the datatype you are trying to store matches what you are storing!

    eg: A float in four bytes read as a four byte integer would look a lot like what you are seeing!

  • Now reading this not on my phone so that I can see your code.

    You are storing float values (the output of Math.atan2(), Math.sqrt() etc) as SINT_32.

    To give you an idea of the problems this might cause, have a look at : https://www.h-schmidt.net/FloatConverter/IEEE754.html

    EG:

    654 as a signed integer is: ‭001010001110

    But as a float it would be: 01000100001000111000000000000000

    Try using DATA_TYPE_FLOAT

    developer.garmin.com/.../FitContributor.html‬

  • Former Member
    0 Former Member over 5 years ago in reply to 9635560

    Thanks for your answer!


    I understand your thought, but I think I'm actually storing the float values as float values. I'm using the Math.atan2() functions only for the pitchField and the rollField and those fields I'm declaring as DATA_TYPE_FLOAT:

    pitchField = session.createField("Pitch_Values", PITCH_FIELD_ID, FitContributor.DATA_TYPE_FLOAT, {:count => numbersPerField, :units => "dg"});
    rollField = session.createField("Roll_Values", ROLL_FIELD_ID, FitContributor.DATA_TYPE_FLOAT, {:count => numbersPerField, :units => "dg"});

    Or am I getting it somehow wrong?

    Tim

  • Ok, I've paid more attention to your code this time.

    Am I wrong, or are you setting the value to an array?

    xAccelField.setData(xAccel.slice(... ) );

    Slice returns;

    "Get a new Array containing a portion of an existing Array."

  • Former Member
    0 Former Member over 5 years ago in reply to 9635560

    Yes exactly. I get the sensor reading every 125ms, and save it in an array (xAccel, yAccel...) Every 8th time I am getting the last 8 values of the array with the xAccel.slice() method and save that array in the FIT-Field. I wanna save several values at once.

    If I log the Accelerometer with a logger-object it also saves several values (25, the maxSampleRate) at once:

    I wanted to get the same result in my own Fit-Field. How do I do that?

  • You just use the index to specify it.

    EG: 

    xAccelField.setData(xAccel.slice(... ) [0] );

  • ETA: Sorry, are you trying to save a single value, or are you trying to save the ENTIRE array.slice?

    If it is the former, my reply holds.

    If it is the latter... you need a fitfield for each value.

  • Former Member
    0 Former Member over 5 years ago in reply to 9635560

    Ah ok thanks. I'm trying to save the entire array.slice. I thought one FIT Field can contain several values. I wanted to save all the values of the X-Axis of the Accelerometer in one Field, the values of the Y-Axis in another Field and so on.

    So if I for example wanna save 5 seconds of data and I get 8 values per second of each sensor and each axis, I will have to create 40 FIT-Fields per Sensor per axis?

    So 40 FIT-Fields for the x-axis of the accel, 40 for the y-axis and so on?

    I mean in the end I just wanna have the reading of the accel and magnetometer in excel, so I can view and continue working with the data there. Maybe there is an easier way to get that?

  • Pretty much, yes.

    But there are hard limits on what you can store... Jim keeps saying somewhere around 16 fields in total.

    These fields are basic summary data, they aren't intended to be an Excel spreadsheet! Have a look at what the activity report looks like when you get too many fields and you'll begin to see why!

    And if you want to store strings... well... that's just painful. There are some notional hard limits on size, but the memory hit often means you can get nowhere near there.

  • I mean in the end I just wanna have the reading of the accel and magnetometer in excel, so I can view and continue working with the data there. Maybe there is an easier way to get that?

    If it were me... I would try to find a way to do it in the IDE and then Toybox.System.println() it out as a tab separated string to the console and cut and paste from there direct into Excel.