First, there was the issue of stopping the list halfway through a scroll. If you start dragging the list and then stop, wait a little and then release the finger or stylus, the list would still scroll. This is not an intended (nor intuitive) behavior: the user scrolls the list up to a position and he / she wants it to stay put by stopping the finger / stylus for a fraction of a second and then releasing it.
The second issue happened when the list was "bouncing back" if you forced it to scroll down from the top (or scrolling up from the bottom). Under some occasions you could actually stop the list from scrolling back to its "rest" position leaving it in an awkward state.
To solve the first issue I changed the bulk of the code in the CTouchGesture class and turned it into a state machine with four inputs:
- Press - The user pressed the finger / stylus
- Move - The user is dragging the finger / stylus
- Release - The user released the finger / stylus
- Timer - Called every 200 ms in order to check transient conditions
By implementing the gesture recognition as a state machine we get a much better chance of determining and handling the harder to detect situations, such as:
- Input noise such as when the user flicks and accidentally releases the screen for a very short period. This is now handled by the code and the state machine assumes that the previous flick is still happening.
- Intermediate motion stop, such as when the user is flicking and stops halfway. This situation is detected by the timer event that essentially resets all displacement and time accumulators and assumes that the user wants to do nothing (this is not interpreted as a click, of course).
To illustrate all of this, I turned back to the AppStart sample simply because it has a bigger list. Here it is for your viewing pleasure (or not...):
Sample code: AppStart03.zip (166 KB)