supporting both physical button and touch input

I find it very hard to support "correct"/user friendly input for an app across different devices.

On example:

I made it work with behaviordelegate. As an example let's look at onSelect. Works fine on devices with physical select button.

But/and It also "works" on devices without select button. For example on edge devices (ee2) a touch of the screen generates onSelect. This could be OK, though I don't like it.

And on watches ie: fr965 that both are touch screen and have a physical select button it kind of works: either I click the button or when I touch the screen anywhere an onSelect event is generated.

However I'd like to be more user friendly and be able to know where the screen was tapped, and react accordingly. This could be achieved by disabling the onSelect (for example by removing the onSelect method using an annotation) and thus onTap will be called when the screen is touched, which is good, but when a user clicks the physical button then nothing happens.

Ideally I would hope that I could disable the translation of taps to onSelect from the code. Or onTap should be called before onSelect. But to my knowledge none of this is possible. Are they?

So the only way I can think of supporting "both" touch and physical buttons is by adding a stupid, unnecessary user setting where they can disable the physical buttons. When they chose this setting then onSelect would return false => onTap will be called.

Does anyone have a good solution for this?

  • see if there are (key) behaviors for all 3 behavior I use in my app: onSelect, onMenu, onBack, and if yes, then it's a hybrid, in which case I can display the option to disable touch.

    TL;DR, no the way to detect a hybrid watch is to see if any physical keys map to onNextPage or onPreviousPage. (But perhaps my definition of "hybrid" is different than yours)

    By your definition above, only Vivoactive 3 series (4 watches) would be "mandatory touch" watches, as all of the other Vivoactive and Venu watches (for example) have a way to trigger onSelect, onMenu, and onBack via either short press or long press of a physical button. That seems like it would only be a suitable definition for an app which doesn't support scrolling or for which scrolling is unimportant. Perhaps that is what you had in mind.

  • So now what I need is a way to determine which devices can I display the setting to disable touch. In other words I need a way to differentiate between "hybrid" and "mandatory touch" devices.

    I assume that:

    "hybrid" = 5-button watches with touch like Forerunner 955, FR265, FR965, Fenix 7, Fenix 8. Almost all functions can be used without touch. [Natively, there's a few things that can't be done without touch, like opening a complication or panning most glance graphs]

    "mandatory touch" = touchscreen watches with less than 5 buttons like all Vivoactives and all Venus. [There's many crucial functions which can't be done without touch, like scrolling]

    (however, you will see below that there is a 5-button watch would could be considered "mandatory touch" - FR630, which has 5 buttons, but the touchscreen is required for scrolling)

  • My current idea is to look in simulator.json for .keys and see if there are (key) behaviors for all 3 behavior I use in my app: onSelect, onMenu, onBack, and if yes, then it's a hybrid, in which case I can display the option to disable touch.

    *In general* because most "mandatory touch" watches (in this case, meaning Vivoactive series or Venu series) already support all of the onSelect, onMenu and onBack behaviours via key presses. (But again, perhaps I am using a different definition of "mandatory touch" than you.)

    For example, Vivoactive 5 only has 2 buttons, but all 3 behaviours are supported by button presses. onSelect = short press of top button, onBack = short press of bottom button, onMenu = long press of bottom button

    vivoactive5/simulator.json:

     "image": "vivoactive5.png",
        "keys": [
            {
                "behavior": "onSelect",
                "id": "enter",
                "location": {
                    "height": 98,
                    "width": 61,
                    "x": 488,
                    "y": 257
                }
            },
            {
                "behavior": "onMenu",
                "id": "menu",
                "isHold": true,
                "location": {
                    "height": 96,
                    "width": 54,
                    "x": 488,
                    "y": 512
                }
            },
            {
                "behavior": "onBack",
                "id": "esc",
                "location": {
                    "height": 96,
                    "width": 54,
                    "x": 488,
                    "y": 512
                }
            }
        ],

  • As another example, Venu 3 series has 3 buttons, and the top 2 buttons work like VA5 with regards to onSelect, onMenu and onBack.

    By your definition above, the only "mandatory touch" watch would be the Vivoactive 3 series (4 watches), which has a single button. A short press of that button works as onSelect, but only in activities (anywhere else, such as in widget, it returns the user to the watchface). For touch, onSelect = tap screen, onBack = swipe right, onMenu = long press screen.

    Somehow I doubt you meant to define "mandatory touch" as 4 watches out of the hundreds of CIQ devices. Or maybe you did?

    Perhaps that definition would work for an app which doesn't require any kind of paging/scrolling, but even you (a year ago) implied that some sort of scrolling or panning might be involved in your app. (Sorry if what you said a year ago is no longer relevant, but you chose to bump this year old thread.)

    So the real way to detect whether a touchscreen watch is "hybrid" (as opposed to "mandatory touch") is to check whether any keys map to onNextPage or onPreviousPage. None of lifestyle/fitness watches that have less than 5 buttons have any way to scroll using buttons.

    Note that there's also the weird Forerunner 630 that has a touchscreen and 5 "keys" (4 physical buttons: START, LIGHT, BACK, LAP; 1 touch-sensitive button: MENU), and no way to scroll with buttons. That's right, all 3 of the onBack, onLap, and onMenu functions have *dedicated* buttons, and you have to use the touchscreen to scroll. By *my* definition of "mandatory touch" (no way to scroll with physical buttons), FR630 would be a mandatory touchwatch (and I think it makes sense tbh).

  • Circling back to your original definitions of "hybrid" and "mandatory touch":

    So now what I need is a way to determine which devices can I display the setting to disable touch. In other words I need a way to differentiate between "hybrid" and "mandatory touch" devices. Ideally this would be some data I can dig up with a script from compiler.json and simulator.json or the debug.xml.

    My current idea is to look in simulator.json for .keys and see if there are (key) behaviors for all 3 behavior I use in my app: onSelect, onMenu, onBack, and if yes, then it's a hybrid, in which case I can display the option to disable touch.

    [1/2]

  • [2/2]

    By your definition above, the only "mandatory touch" watch would be the Vivoactive 3 series (4 watches), which has a single button. A short press of that button works as onSelect, but only in activities (anywhere else, such as in widget, it returns the user to the watchface). For touch, onSelect = tap screen, onBack = swipe right, onMenu = long press screen.

    Somehow I doubt you meant to define "mandatory touch" as 4 watches out of the hundreds of CIQ devices. Or maybe you did?

    Perhaps that definition would work for an app which doesn't require any kind of paging/scrolling, but even you (a year ago) implied that some sort of scrolling or panning might be involved in your app. (Sorry if what you said a year ago is no longer relevant, but you chose to bump this year old thread.)

    If your definition of "mandatory touch" actually is what you say it is, then I guess by "mandatory touch" you literally meant "mandatory". I think I get it - you want there to be a way to re-enable the touchscreen after the user disables it.

    Then I would say there's 3 kinds of touchscreen watches [if the "mandatory touch" category is useful to you]:

    1) "mandatory touch": devices where not all of onSelect, onMenu, and onBack are mapped to buttons. Perhaps this suggests to you that you literally cannot disable touch otherwise you won't be able re-enable it (but we'll see this isn't true at all). i.e Vivoactive 3 series and no other watches

    2) "touch-first": devices where crucial functions like scrolling require touch, but all of onSelect, onMenu, and onBack are mapped to buttons. e.g. Vivoactive series (except 3) and Venu series

    3) "touch-optional": devices where all crucial functions can be done with buttons alone. e.g. Forerunner 265, 955, 965; Fenix 7 series

    But what's the real difference between 1) and 2)? Natively, both kinds of watches allow you to lock the touchscreen, meaning that there must be some way to unlock the touchscreen. And there is: by holding any button. (This means there are is no such thing (natively) as a "mandatory touch" watch (taking the literal meaning of mandatory))

    So there's no reason your app can't do the same for *all* touchscreen devices, unless it's not possible to detect a long press of the single button on VA3.

    But then again, how will a user of a "touch-first" device re-enable touch in your app? Clearly it can't just be through a normal settings menu (opened with a button), as they would likely need a way to scroll through the menu in order to activate the touch option, unless you strategically arrange it so that no scrolling is required. This would kind of be a bad user experience, though: giving the user a menu where only one option out of many can be changed.

    It seems that the best way to unlock touch would be to do something similar to what the native firmware does (if possible): unlock touch with any long button press. Or if that's no possible (probably not with VA3), maybe unlock touch by long-pressing and/or swiping the touchscreen.

  • In other words, if your real criteria for a "mandatory touch device" is "inability to disable touch", there's no such Garmin watch at all. Natively, every touchscreen watch can lock / unlock the touchscreen.

    If the real criteria for "mandatory touch" is "does not have all of onBack, onMenu and onSelect mapped to physical keys", then only the Vivoactive 3 series are "mandatory touch" devices. But that kind of raises the question of *why* you need those keys to be mapped to physical buttons in order to disable touch. Is it so the user can re-enable touch via a menu or something? In that case, even users of watches like VA5 and Venu which have all 3 of those behaviours on physical keys would have trouble navigating a menu without the touchscreen.

    All of this raises another question: why does your app need a way to disable touch when this is already a built-in feature on touchscreen watches? (To be fair FR630 only allows you to lock *both* the touchscreen and keys. Not sure if any other watches are like this)

    To answer your question about detecting "mandatory touch" vs. "hybrid" devices properly, I would need a definition of "mandatory touch" which explains why touch is supposedly "mandatory" on those devices.

  • Devices that work fine with touch or buttons, like some of the newer 5 button watches, have a standard setting to disable touch.

    Trying to do this yourself required your own setting, and then it might be OK for a simple app with only CIQ views, but for native views, like MapView/MapTrackView/Menu2 it won't - they handle their own input.

  • Devices that work fine with touch or buttons, like some of the newer 5 button watches, have a standard setting to disable touch.

    As noted above, all touchscreen watches have a way to disable (lock) touch, even watches where crucial functions like scrolling require the touchscreen, such as all Vivoactive and Venu watches.

  • Lock is different.  With that, buttons are also disabled except for the unlock method. What I'm talking about disables touch, but all buttons are still available.