由Using UIPageViewController with swift and multiple view controllers提供,我在UIPageViewController
中嵌入了导航控制器,因此我可以通过它们水平滚动(如滑动导航)。问题:
当我到达第一个或最后一个导航控制器,然后向相反方向滑动时,第二个到第一个/最后一个导航控制器将复制。所以我将有5个导航控制器。例如:
从FirstNav开始,向左滑动到FourthNav。当我从FourthNav向右滑动控制器阵列时,序列将是:ThirdNav,ThirdNav,SecondNav,FirstNav。有人能找出发生了什么吗?
class PageViewController: UIPageViewController, UIPageViewControllerDataSource, UIPageViewControllerDelegate {
var index = 0
var identifiers: NSArray = ["FirstNav", "SecondNav", "ThirdNav", "FourthNav"]
override func viewDidLoad() {
super.viewDidLoad()
self.dataSource = self
self.delegate = self
let startingViewController = self.viewControllerAtIndex(self.index)
let viewControllers: NSArray = [startingViewController]
self.setViewControllers(viewControllers as [AnyObject], direction: UIPageViewControllerNavigationDirection.Forward, animated: false, completion: nil)
}
func viewControllerAtIndex(index: Int) -> UINavigationController! {
if index == 0 {
return self.storyboard!.instantiateViewControllerWithIdentifier("FirstNav") as! UINavigationController
}
if index == 1 {
return self.storyboard!.instantiateViewControllerWithIdentifier("SecondNav") as! UINavigationController
}
if index == 2 {
return self.storyboard!.instantiateViewControllerWithIdentifier("ThirdNav") as! UINavigationController
}
if index == 3 {
return self.storyboard!.instantiateViewControllerWithIdentifier("FourthNav") as! UINavigationController
}
return nil
}
func pageViewController(pageViewController: UIPageViewController, viewControllerAfterViewController viewController: UIViewController) -> UIViewController? {
let identifier = viewController.restorationIdentifier
let index = self.identifiers.indexOfObject(identifier!)
//if the index is the end of the array, return nil since we dont want a view controller after the last one
if index == identifiers.count - 1 {
return nil
}
//increment the index to get the viewController after the current index
self.index = self.index + 1
return self.viewControllerAtIndex(self.index)
}
func pageViewController(pageViewController: UIPageViewController, viewControllerBeforeViewController viewController: UIViewController) -> UIViewController? {
let identifier = viewController.restorationIdentifier
let index = self.identifiers.indexOfObject(identifier!)
//if the index is 0, return nil since we dont want a view controller before the first one
if index == 0 {
return nil
}
//decrement the index to get the viewController before the current one
self.index = self.index - 1
return self.viewControllerAtIndex(self.index)
}
func presentationCountForPageViewController(pageViewController: UIPageViewController) -> Int {
return 0
}
func presentationIndexForPageViewController(pageViewController: UIPageViewController) -> Int {
return 0
}
}
答案 0 :(得分:2)
问题与您在index
和pageViewController(_:viewControllerBeforeViewController:)
方法中计算pageViewController(_:viewControllerAfterViewController:)
变量有关。要简化逻辑和页面视图控制器的整体逻辑,您应该将实现更改为以下内容:
class PageViewController: UIPageViewController, UIPageViewControllerDataSource, UIPageViewControllerDelegate {
private var pages: [UIViewController]!
override func viewDidLoad() {
super.viewDidLoad()
self.dataSource = self
self.delegate = self
self.pages = [
self.storyboard!.instantiateViewControllerWithIdentifier("FirstNav") as! UINavigationController,
self.storyboard!.instantiateViewControllerWithIdentifier("SecondNav") as! UINavigationController,
self.storyboard!.instantiateViewControllerWithIdentifier("ThirdNav") as! UINavigationController,
self.storyboard!.instantiateViewControllerWithIdentifier("FourthNav") as! UINavigationController
]
let startingViewController = self.pages.first! as UIViewController
self.setViewControllers([startingViewController], direction: .Forward, animated: false, completion: nil)
}
func pageViewController(pageViewController: UIPageViewController, viewControllerAfterViewController viewController: UIViewController) -> UIViewController? {
let index = (self.pages as NSArray).indexOfObject(viewController)
// if currently displaying last view controller, return nil to indicate that there is no next view controller
return (index == self.pages.count - 1 ? nil : self.pages[index + 1])
}
func pageViewController(pageViewController: UIPageViewController, viewControllerBeforeViewController viewController: UIViewController) -> UIViewController? {
let index = (self.pages as NSArray).indexOfObject(viewController)
// if currently displaying first view controller, return nil to indicate that there is no previous view controller
return (index == 0 ? nil : self.pages[index - 1])
}
}
您甚至不需要维护index
实例变量,并且此实现不会这样做。但如果你愿意,你可以。此解决方案还实例化每个UINavigationController
的单个实例,而不是每次用户尝试滚动到不同的页面时实例化新的实例,这保留了内存并在用户在它们之间滚动时保留视图控制器的状态。
请原谅非描述性pages
变量名称。我不想与UIPageViewController
的{{1}}属性发生冲突。