Swipe to go back only works on edge of screen?

后端 未结 3 1056
失恋的感觉
失恋的感觉 2020-12-10 22:48

My swipe to go back feature works but only works on the edge of the screen. How can I have it work from anywhere on the screen?

相关标签:
3条回答
  • 2020-12-10 23:00

    Swipe to go back is default behavior of pushed/showed view controllers. It works from left edge of the screen (by default). If you want to swipe back from any part of the screen, you should add UISwipeGestureRecognizer to your view:
    let swipeGestureRecognizer = UISwipeGestureRecognizer(target: self, action: "didSwipe:") self.view.addGestureRecognizer(swipeGestureRecognizer)

    0 讨论(0)
  • 2020-12-10 23:01

    Apple says here :

    interactivePopGestureRecognizer

    The gesture recognizer responsible for popping the top view controller off the navigation stack. (read-only)

    @property(nonatomic, readonly) UIGestureRecognizer *interactivePopGestureRecognizer

    The navigation controller installs this gesture recognizer on its view and uses it to pop the topmost view controller off the navigation stack. You can use this property to retrieve the gesture recognizer and tie it to the behavior of other gesture recognizers in your user interface. When tying your gesture recognizers together, make sure they recognize their gestures simultaneously to ensure that your gesture recognizers are given a chance to handle the event.

    So SloppySwiper library customise the UIPanGestureRecognizer.

    Check out the library SloppySwiper, which achieves this by using UIPanGestureRecognizer and by recreating the default animation.

    SloppySwiper:- UINavigationController delegate that allows swipe back gesture to be started from anywhere on the screen like instagram.

    Usage of this library can be found here.

    Cocoapods:- pod "SloppySwiper"

    I test this library on ios7 and above. It works like a charm.

    0 讨论(0)
  • 2020-12-10 23:14

    It's actually quite easy to do on the UINavigationController subclass without any intervention into every UIViewController subclass pushed. Also respecting built-in swipe-from-edge state (so when it's disabled intentionally, the new gesture is disabled as well):

    import UIKit
    
    class NavigationController: UINavigationController {
        override func viewDidLoad() {
            super.viewDidLoad()
            setupFullWidthBackGesture()
        }
    
        private lazy var fullWidthBackGestureRecognizer = UIPanGestureRecognizer()
    
        private func setupFullWidthBackGesture() {
            // The trick here is to wire up our full-width `fullWidthBackGestureRecognizer` to execute the same handler as
            // the system `interactivePopGestureRecognizer`. That's done by assigning the same "targets" (effectively
            // object and selector) of the system one to our gesture recognizer.
            guard
                let interactivePopGestureRecognizer = interactivePopGestureRecognizer,
                let targets = interactivePopGestureRecognizer.value(forKey: "targets")
            else {
                return
            }
    
            fullWidthBackGestureRecognizer.setValue(targets, forKey: "targets")
            fullWidthBackGestureRecognizer.delegate = self
            view.addGestureRecognizer(fullWidthBackGestureRecognizer)
        }
    }
    
    extension NavigationController: UIGestureRecognizerDelegate {
        func gestureRecognizerShouldBegin(_ gestureRecognizer: UIGestureRecognizer) -> Bool {
            let isSystemSwipeToBackEnabled = interactivePopGestureRecognizer?.isEnabled == true
            let isThereStackedViewControllers = viewControllers.count > 1
            return isSystemSwipeToBackEnabled && isThereStackedViewControllers
        }
    }
    
    0 讨论(0)
提交回复
热议问题