2

I have an FSPagerView, which has an item that contains scrollable barchart (scrollview having multiple stackviews). When I scroll barchart, if there is a scrollable space, then touch event is consumed by the barchart and it scrolls. If there is no scrollable space on a side and I keep scrolling to that side touching barchart, it does not consume touch event anymore and instead the whole FSPagerView scrolls. How can I make scrollview consume touch event even in such case? In short, I don't want to scroll FSPagerView when touching barchart.

Here is a video: https://streamable.com/kuxta

Gintas_
  • 4,940
  • 12
  • 44
  • 87

3 Answers3

3

You can prioritize the UIGestureRecognizer of the two scroll views using the require(toFail:) method.

Here is the code I tried:

scrollView.panGestureRecognizer.require(toFail: collectionView.panGestureRecognizer)

I don't know if it's exactly what you were looking for. As soon as the collectionView.panGestureRecognizer detects something, the scroll view won't scroll.

GaétanZ
  • 4,870
  • 1
  • 23
  • 30
  • I get NSInvalidArgumentException "UIScrollView's built-in pan gesture recognizer must have its scroll view as its delegate" – Gintas_ May 29 '19 at 18:31
  • I tried subclassing scrollview, overriding this method, it gets called, but then I can't swipe barchart at all. When I swipe it, pager view swipes. I tried reverting the condition with negation, but then the initial problem becomes present again – Gintas_ May 29 '19 at 18:39
  • would you provide a working example? I tried subclassing with no luck – Gintas_ May 29 '19 at 19:40
  • I tried your code, it made the scroll of barchart impossible. When I try to scroll barchart, pagerview is always scrolled. Then I reversed it so that collection view's recognizer fails scrollview's recognizer and it looks fine. Thanks! – Gintas_ Jun 03 '19 at 06:42
1

You can try to manipulate UIScrollView's gesture recognizer:

scrollView.panGestureRecognizer

I never tested it with UIScrollView's panGestureRecognizer, but general idea is to add a gesture recognizer to FSPagerView and to set relations (using UIGestureRecognizer's delegate) between that recognizer and panGestureRecognizer to prevent it from firing

Krypt
  • 434
  • 4
  • 12
  • can you provide a more detailed code example? Otherwise the answer is useless – Gintas_ May 29 '19 at 11:53
  • Ok, I will add an example, probably tomorrow. Honestly, I don't remember exact method names, so it requires some experimentation, but I have no spare time to do so :( – Krypt May 29 '19 at 15:08
1

FSPagerView exposes panGestureRecognizer that is essentially the underlying UICollectionView's panGestureRecognizer.

I think you can just disable it while you are seeing the barchart.

Not very familiar with FSPagerView, but I think you can detect in which page you are by monitoring FSPagerViewDelegate callbacks. For example, if the bar chart is in the first page (i.e., index == 0), probably you can do something like this.

override func pagerView(_ pagerView: FSPagerView, willDisplay cell: FSPagerViewCell, forItemAt index: Int) {
    // FSPagerView's gesture recognizer is only enabled for index > 0.
    pagerView.panGestureRecognizer.isEnabled = (index != 0)
}

If that callback does not work, I would try the same thing with func pagerView(_ pagerView: FSPagerView, didSelectItemAt index: Int) callback.

barley
  • 4,403
  • 25
  • 28