4

I have a NavigationLink view that contains a ScrollView that mainly shows a list of contacts. However, the ScrollView sometimes register user's pop gesture as a scrolling gesture, thereby preventing the user swipe back out of the NavigationLink view.

The general structure is like the follow:

struct ContentView: View {
    var body: some View {
        NavigationView {
            NavigationLink (destination: AnotherView()) {Text("enter")}
        }
    }
}

struct AnotherView: View {
    var body: some View {
        ScrollView {
            LazyVStack(alignment: .leading) {
             // ... a list of things
            }
        }
    }
}

Is there anyway to tell ScrollView to ignore the horizontal-ish drag gestures so that NavigationLink can be swiped out properly and smoothly?

PipEvangelist
  • 601
  • 1
  • 7
  • 22
  • Hope this helps https://stackoverflow.com/questions/59438285/disable-swipe-back-for-a-navigationlink-swiftui – Okeyman Nov 13 '21 at 22:33

2 Answers2

4

I had a similar problem with TabView. The following extension solved it:

extension UINavigationController: UIGestureRecognizerDelegate {
override open func viewDidLoad() {
    super.viewDidLoad()
    interactivePopGestureRecognizer?.delegate = self
}

// Allows swipe back gesture after hiding standard navigation bar with .navigationBarHidden(true).
public func gestureRecognizerShouldBegin(_ gestureRecognizer: UIGestureRecognizer) -> Bool {
    viewControllers.count > 1
}

// Allows interactivePopGestureRecognizer to work simultaneously with other gestures. 
public func gestureRecognizer(_ gestureRecognizer: UIGestureRecognizer, shouldRecognizeSimultaneouslyWith otherGestureRecognizer: UIGestureRecognizer) -> Bool {
    viewControllers.count > 1
}

// Blocks other gestures when interactivePopGestureRecognizer begins (my TabView scrolled together with screen swiping back)
public func gestureRecognizer(_ gestureRecognizer: UIGestureRecognizer, shouldBeRequiredToFailBy otherGestureRecognizer: UIGestureRecognizer) -> Bool {
    viewControllers.count > 1
}
}

Hope this will be helpful.

IronHead
  • 76
  • 5
2

I made it work by attaching .gesture(DragGesture(minimumDistance: 20)) to my ScrollView so that the pop gesture of NavigationView has a higher priority over ScrollView's gesture.

PipEvangelist
  • 601
  • 1
  • 7
  • 22