Suppose you have a View configuration like this.
With "UIViewController-D" displayed in the push transition from "UIViewController-C" on the UINavigationController, I want to return to "UIViewController-C" by swiping on the left edge of the screen (blue arrow). The actual operation is "UIViewController-A" is displayed (red arrow). Apparently, the UIPageViewController's swipe gesture is prioritized over the UINavigationController's swipe gesture ...
I was able to disable swipes by setting the UIPageViewController's dataSource to nil. When UIViewController-D was displayed, I was able to solve the problem by posting a Notification to UIPageViewController, setting the dataSource to nil, and returning it when the screen disappears.
class PageViewController: UIPageViewController {
static let needToChangeSwipeEnabledNotification = Notification.Name("NotificationForChangeMainPageSwipeEnabled")
override func viewDidLoad() {
super.viewDidLoad()
dataSource = self
NotificationCenter.default
.addObserver(forName: PageViewController.needToChangeSwipeEnabledNotification,
object: nil,
queue: nil,
using: { [weak self] notification in
guard let canSwipe = notification.object as? Bool else { return }
self?.changeSwipeEnabled(to: canSwipe)
})
}
private func changeSwipeEnabled(to canSwipe: Bool) {
dataSource = canSwipe ? self : nil
}
//abridgement
}
class ViewController_D: UIViewController {
//abridgement
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
NotificationCenter.default.post(name: PageViewController.needToChangeSwipeEnabledNotification, object: false)
override func viewDidDisappear(_ animated: Bool) {
super.viewDidDisappear(animated)
NotificationCenter.default.post(name: PageViewController.needToChangeSwipeEnabledNotification, object: true)
}
}
Recommended Posts