Flutter: Make it easy to override Scrollable's gesture detectors, e.g. to enable scale+scroll

Created on 1 Mar 2018  路  8Comments  路  Source: flutter/flutter

Currently if you want a Scrollable that can both be scaled and scrolled, you have to have separate Scale and VerticalDrag gesture detectors, the scale in your code, and the vertical drag in the Scrollable. This makes the UI ugly, because it means the user has to know which operation they are doing when they begin, and if they move one finger as they're putting the second down, it'll trigger the scroll instead of the scale.

Another use case is two orthogonal Scrollables sharing a single Pan gesture detector.

We should make it easy to override how Scrollable listens to gestures.

P5 crowd gestures scrolling framework new feature

Most helpful comment

I believe I have a very similar issue here with a slightly different use case so chiming in to provide more info.

I have a widget that uses a GestureDetector to capture onPan events, that is placed inside a scroll view. When trying to pan within the widget, it gesture is often decided to be a scroll and ends up scrolling the widget instead of panning within it. If I add a onVerticalDrag handlers to the GestureDetector, it stops this behaviour, but then the panning doesn't happen correctly (the gesture is locked into a vertical scroll and doesn't transition to a pan, I need horizontal movement too).

I'd like a way to instruct: only pan within this widget, even if the gesture at first seems like a scroll.

All 8 comments

I'm working on a custom chart view where the user can scroll the chart horizontally, and also use scale gestures to zoom the chart in and out.

Currently my solution is based on a CustomScrollView with a sliver adapter which draws only the visible part of the chart.
I ran into the issue you mention here: since I couldn't override Scrollable's gesture detector, I had to add a new GestureDetector to the view hierarchy in order to detect scale gestures but that caused two unwanted side effects:

  1. As mentioned in the issue description, it's hard to perform the scale gesture since it gets easily interpreted as a scrolling gesture.
  2. When scrolling, you need to move the finger more than a certain amount of pixels before the gesture disambiguator realizes it's a scrolling gesture, causing the view to suddenly jump to the new scroll position. This looks janky and makes it hard to precisely adjust the scroll position.

I've uploaded a sample project which demonstrates the problem here: https://github.com/cachapa/flutter_scale_scroll
I hope having a concrete use case and a bare-bones implementation will expedite solving this issue.

I also hit this problem. Combined scaling and scrolling is not user-friendly right now. The gesture detector in Android does a better job when it comes to this. A good example would be the Google Maps, where you can start panning with a single finger, and by putting down a second finger, scaling starts immediately.

The idea to have many separate GestureDetectors which compete in an arena works for simple cases, but it does not really reflect the reality of gesture detection.

I believe I have a very similar issue here with a slightly different use case so chiming in to provide more info.

I have a widget that uses a GestureDetector to capture onPan events, that is placed inside a scroll view. When trying to pan within the widget, it gesture is often decided to be a scroll and ends up scrolling the widget instead of panning within it. If I add a onVerticalDrag handlers to the GestureDetector, it stops this behaviour, but then the panning doesn't happen correctly (the gesture is locked into a vertical scroll and doesn't transition to a pan, I need horizontal movement too).

I'd like a way to instruct: only pan within this widget, even if the gesture at first seems like a scroll.

25164 looks related

@zoechi that pull request seems to implement a simple example using an indepentent GestureDetector.

This ticket concerns exposing the ScollView's GestureDetector in order to implement gestures like scale without having to add another detector, which has a bad user experience due to gesture disambiguation.

I also need this feature.
I expect to be in a listview, when it is at the beginning, pull down, the gesture will be passed to the next layer.

This solved my problem: https://medium.com/flutter-community/flutter-deep-dive-gestures-c16203b3434f
Just swap out the TapGestureRecognizer with ScaleGestureRecognizer.

This isn't an exact solution to the problem here, but just making a note that InteractiveViewer is now available and can handle scaling and scrolling.

Was this page helpful?
0 / 5 - 0 ratings