fermoya / SwiftUIPager

Native Pager in SwiftUI
MIT License
1.27k stars 168 forks source link

[BUG] With vertical pagination, it interferes with horizontal swipe in `TabView` on watchOS #274

Closed andriy-appuchino closed 2 years ago

andriy-appuchino commented 2 years ago

Describe the bug There is a problem on watchOS. If Pager is in TabView like in an example, then switching between tabs from left to right very often does not work. Probably Pager is blocking gestures horizontally somewhere.

To Reproduce

  1. Download and unzip PagerInTabView.zip
  2. Run project on simulator or watch2.
  3. Try swiping left or right on a screen with vertical pagination (yellow or red background).
  4. Horizontal swipe very often does not work.

Expected behavior Stable operation of swipe left and right every time.

Screenshots / Videos

https://user-images.githubusercontent.com/49787488/162640669-19e93316-f19a-4a39-9f3b-d0fcc2086ca9.mov

Environment:

Additional context Pay attention that on other screens where Pager is not used (green or blue background) horizontal swipe works in 100% of cases.

fermoya commented 2 years ago

@andriy-appuchino apologies but I haven't had time to look at this and I don't think I will within the next days.

Some people have mentioned this same experienc, here are some hints that would solve this issue:

Hope that helps. I don't think there's much more to do here if TabView doesn't work with a simultaneous gesture. SwiftUI doesn't offer an alternative to DragGesture which is more like a UIPanGesture and not a UISwipeGesture

andriy-appuchino commented 2 years ago
  1. Just using pagingPriority(.simultaneous) doesn't help.
  2. I tried to use a horizontal Pager, but the problem is no less serious with it. If there are buttons on the page, then they are constantly accidentally pressed when swiping. Normally, if the beginning of the movement of the finger hits the button, then it should not trigger.

@fermoya do you know how to fix case 2?

By the way, the horizontal Pager should use the modifier mentioned in the previous bullet, not the vertical one.

fermoya commented 2 years ago

@andriy-appuchino have you tried using onTapGesture or gesture(TapGesture().onEnded {}) instead of a Button? That could do the trick, I believe that if swiping, those gestures should get canceled and the callbacks should never be called. Same can't be said about Button, but it's just a guess

andriy-appuchino commented 2 years ago

No, I haven’t, I don’t want to give up buttons so as not to lose their visual effects.

I was able to interrupt a button touch in during a swipe using .disabled(areControlsDisabled) and

.onDraggingBegan({
     areControlsDisabled = true
})
.onDraggingEnded({
     areControlsDisabled = false
})

Nevertheless, thanks for the help.

P.S. I recommend disabling digitalCrownRotation by default for the horizontal Pager, because it is very unusable.

fermoya commented 2 years ago

Closing this as it's a similar problem as #153