Data Field: AppBuilder

By user request, this app lets you define your own data field, based on a simple math formula like cadence / 2.

If you want to get fancy, there's conditional expressions (like IF in Excel), functions for data analysis (like MIN and AVG), and the data field can also display the text of your choice. The resulting data can be (optionally) written to the activity FIT file.

With AppBuilder, you can implement almost any field that involves math, such as: calculating normalized power and saving the data to the FIT activity file, showing the average pace for even-numbered laps, or recording the amount of time you sprinted.

Full documentation and examples here:
http://ciq-appbuilder.blogspot.com/

AppBuilder 5:
Now with new features! AppBuilder 5 is a completely new app, so please check it out in the store if you are interested in any of the new features.
https://apps.garmin.com/en-US/apps/fd690281-9c22-4fee-a81e-3b7f39aa67c5

- Store up to four formulas per app. Switch between formulas directly on the watch, without using a phone or PC. With four clone apps, you can store up to 16 formulas total
- User variables. Allows for powerful formulas where information can be stored at one point, like the start of a lap, and used later. e.g. Lap elevation change
- Improved timeavg() options. Allows for simpler, more flexible normalized power function
- More functions and variables

4 clones of AppBuilder are available in the store, so you can have 2 formulas in the same activity
  • I moved all the docs and examples to one place:
    http://ciq-appbuilder.blogspot.com/

    It's a little rough right now, but all the information is there

    This will avoid forum issues as well eliminating the need to go to 5 different places to see all the examples.
  • Made a major update to the docs at http://ciq-appbuilder.blogspot.com/. It's broken down into separate pages now, including examples, functions and variables (activity data). The complete lists of variables and functions are at the top of their respective pages, so hopefully it's a lot easier to find what you're looking for.

    The examples are greatly improved: it's visually clear what's part of the formula and what isn't, and there's a button next to each example to copy the formula to the clipboard.
  • Update 5.2 (AppBuilder 5):

    - Add new "pause mode" option for PREV. PREV can now keep/collect data while the timer is paused.
    PREV(X, pauseMode)

    pauseMode (optional)
    0: (default) discards data, returns null while timer is paused
    1: returns old data while timer is paused (does not collect new data)
    2: collects new data while timer is paused

    - Fix examples involving user variables and storing data at beginning of lap. (Laps can be taken while the device is paused)

    - Add new example: Last Lap HR
    SETV(IF (PREV(LapCount, 2) LT LapCount, 1, NULL), PREV(LAPAVG0(HR),2)) ; GETV(1)
  • Big update for CIQ1 devices: Added previously CIQ2-exclusive functions: AVG, AVG0, LAPAVG, LAPAVG0, LOG, GETV/SETV and PREV's pauseMode.

    Now you can calculate Normalized Power or Last Lap HR on older watches, and more of the previously CIQ2-only examples will work now.

    I updated the documentation and fixed a few problems (lap metrics were miscategorized as CIQ2-only, for example).

    Note: On AppBuilder 5 and CIQ1 devices, the Time2 format now does the exact same thing as Time: it formats seconds as [hours:]minutes:seconds. If you need Time2 (minutes:seconds) on CIQ1 devices, please use AppBuilder classic.

    I'm keeping these changes on AppBuilder 5 only for now (and not porting them to AppBuilder Classic). I'm probably not going to update the Classic app except to fix bugs, at this point.
  • Latest update (5.3.3):

    - Fix crash when selecting profile with blank formula
    - Add setting for "Quick Profile Select Hotkey" to help you if you have 2, 3 or 4 AppBuilders in the same activity and you want to switch profiles on the watch.
    Options:
    - Disabled
    - Double-click once [default]
    - Double-click twice
    - Double-click 3 times
    - Double-click 4 times

    Normally you would be unable to configure more than one field independently on the watch, because they all react to the same initial double-click hotkey. This would make the feature for configuring your fields on the watch pretty useless, since they would all be changing in lockstep.

    With this setting, you set each of your AppBuilders to a different hotkey, and you can configure them sequentially. Or you can just disable the hotkey if you don't like it.

    e.g. 3 AppBuilder fields in one activity.
    Set A to "Double-click once", B to "twice" and C to "3 times".

    The first double-click will let you change A's profile
    The second double-click will save A's changes and enter profile selection for B
    The third double-click will save B's changes and enter profile selection for C.

    If you want to skip configuring any of the fields, simply leave the profile unchanged, and the field will return to normal after you exit config mode.
  • Hi I'm just starting to dip my feet into AppBuilder. I've installed AppBuilder 5 on my Fenix 3 & the CIQ 1 configuration for NP

    AVG0(IFS(Timer GTE 30 and (Timer - MAX(IFS (PREV(timer) eq null, timer)) plus 1) gte 30, TIMEAVG0(Power,30)^4))^0.25

    I'm trying to modify this to give my max 20 Min NP for the activity. I thought the configuration might work, however I get a CIQ error when I start the activity. It may be a resource issue on a CIQ1 device, but was wondering if anyone could help me to get it working.

    MAX(TIMEAVG0(AVG0(IFS(Timer GTE 30 and (Timer - MAX(IFS (PREV(timer) eq null, timer)) plus 1) gte 30, TIMEAVG0(Power,30)^4))^0.25, 1200))

    Cheers
  • hotdogpartysausage unfortunately that won't work because:
    -TIMEAVG stores the data for all the samples and most watches (even 935 and Fenix 5 "non-plus") don't have enough memory available to data fields for 1200 samples (in this app)
    - Even if you had enough memory, you want a rolling max over time which is not something that is supported by appbuilder

    There are approximations for the moving average that don't involve storing all the samples (although not available in appbuilder), but I don't think you can calculate a rolling MIN or MAX over time without storing all the samples, so this would never be feasible except for Fenix 5, 645 Music or other devices.

    This is probably the kind of thing that would need to be done in a dedicated data field.

    Having said all that, normalized power is an average (over your entire activity), so:
    - The longer you ride, the less it should change
    - I don't even know what the 20 minute max signifies, in this case (but TBH I'm not a cyclist)

    It would be like taking the lap max of your average lap pace afaik -- an interesting calculation but not sure what it would signify.

    EDIT: Clearly the previous post has nothing to do with rolling min/max. My mistake!
  • Thanks for the detailed explanation. I was hoping there might be a way to do it with appbuilder without creating a dedicated datafield. Never mind

    fwiw. 20 minute power can be used amongst other power intervals to give a rough estimate of cycling FTP. It can be seen retrospectively on completion of an activity & saving. I thought it might be interesting to see real time on a periodic update
  • hotdogpartysausage, oh sorry, I completely misread your post. I thought it was "max NP over 20 minutes" but now I see that it's "max 20 minute NP", which is exactly what you wrote...

    Well, it's not something that's hard to create. Can't make any promises, but I'll look into it. What other combos of NP are useful?
  • Update 5.4:

    Huge update for CIQ2 devices:
    New wrinkles on old functions: FINDLT, FINDGT, FINDLTINDEX, FINDGTINDEX
    New functions: ABS, ALT
    Record to FIT lap info. You can now record completely separate data to the: activity data, lap info and summary
    Support for text! This is something I wanted to add for a long time

    I'll update docs and examples later, but here's a few examples to get you started.

    As always, please change square brackets to round brackets below.

    Strings
    'Hello World!'

    Combining strings and numbers:
    '^' + HR + ' bpm'

    Displaying two values:
    HR + ' / ' + Max
    Recording one value while displaying text
    Record
    ; HR + ' / ' + Max
    Note: once you combine numbers with text, the whole result becomes text [which won't record to the FIT file] and you need to use one of the RECORD functions to record data to the FIT file.

    Controlling FIT recording
    e.g. Record Lap AVG HR to lap data, Max HR to summary, HR to activity data [and display]

    RECORDLAP[ LAPAVG0
    ] ; RECORDSUMMARY[ MAX
    ] ; RECORD
    New Functions
    ALT[X, Y]
    - Returns X if X is not 0 and not NULL, otherwise returns Y
    - e.g. Display HR; if HR is non-zero [and non-null], display 'No HR' otherwise
    ALT[HR, 'No HR']

    FINDLT, etc.
    - Just like FINDLTE, etc., except they match 'less/greater than' instead of 'less/greater than or equal to'

    ABS[X]
    - Returns the absolute value of X

    FORMATNUMBER[x], FORMATDECIMAL[x], , FORMATTIME[x], , FORMATTIME2[x], FORMATPACE[x]
    - Formats X just like the Display Format options in the app settings. Useful for when you combine text with numbers-
    - e.g.
    FORMATNUMBER[LAPAVG
    ] + ' bpm'
    FORMATPACE[LAPAVG[Speed]]

    HR + ' bpm'
    ^ A number without a format is converted according to your app settings

    - RECORD[X], RECORDLAP[X], RECORDSUMMARY[X]
    - Records the number X to the activity data, lap data, or summary data
    - Returns the value you passed in
    - You need this once you start displaying text, because text does not record to the FIT file
    - Also helpful for recording different information to the activity data, summary and lap info.

    - e.g. Record HR and format it differently
    FORMATNUMBER[RECORD[LAPAVG
    ]]
    RECORD[LAPAVG
    ] + ' bpm'