[英]How to change viewController based on device orientation
在过去的几天里,我一直在努力寻找一种方法来做到这一点:
如果在横向模式下,请更改为CollectionViewController。 如果处于纵向模式,请更改为ViewController。
音乐应用程序的行为方式几乎相同。
我这样做的方法是在我的主要portraitViewController类中实现viewWillTransitionToSize():
override func viewWillTransitionToSize(size: CGSize, withTransitionCoordinator coordinator: UIViewControllerTransitionCoordinator) {
let storyBoard = UIStoryboard(name: "Main", bundle: NSBundle.mainBundle())
let portraitViewController = storyBoard.instantiateViewControllerWithIdentifier("portraitViewController") as! ViewController
let landscapeViewController = storyBoard.instantiateViewControllerWithIdentifier("landscapeViewController") as! beerCollectionViewController
if (UIDevice.currentDevice().orientation.isLandscape) {
// In landscape
presentViewController(landscapeViewController, animated: true, completion: nil)
} else {
// In portrait
self.navigationController?.presentViewController(portraitViewController, animated: true, completion: nil)
//let navVC = UINavigationController(rootViewController: portraitViewController)
//presentViewController(navVC, animated: true, completion: nil)
//Dismiss collectionViewController after switching back to portrait
self.dismissViewControllerAnimated(true, completion: nil)
}
}
主viewController(portraitViewController)包含一个表视图和一个顶部具有searchBar的searchController。
在情节提要中,portraitViewController嵌入在导航控制器中,collectionViewController(landscapeViewController)单独存在。
它运行,但是我收到以下2条警告:
尝试在视图不在窗口层次结构中的ViewController上呈现UINavigationController!
不允许在取消分配时尝试加载视图控制器的视图,这可能会导致未定义的行为(UISearchController)
有人可以指出这里出了什么问题吗? 如果有任何教程/示例可以提供帮助,我将不胜感激! 非常感谢你的帮助
编辑 :这是有效的最终代码
override func viewWillTransitionToSize(size: CGSize, withTransitionCoordinator coordinator: UIViewControllerTransitionCoordinator) {
let storyBoard = UIStoryboard(name: "Main", bundle: NSBundle.mainBundle())
// In landscape
if UIDeviceOrientationIsLandscape(UIDevice.currentDevice().orientation) {
let landscapeVC = storyBoard.instantiateViewControllerWithIdentifier("landscapeViewController") as! beerCollectionViewController
if presentedViewController != nil {
if !presentedViewController!.isBeingDismissed() {
self.dismissViewControllerAnimated(false, completion: {
self.presentViewController(landscapeVC, animated: true, completion: nil)
})
}
} else {
self.presentViewController(landscapeVC, animated: true, completion: nil)
}
}
// In portrait
else {
let navC = storyBoard.instantiateViewControllerWithIdentifier("navID") as! UINavigationController
let portraitVC = storyBoard.instantiateViewControllerWithIdentifier("portraitViewController") as! ViewController
if presentedViewController != nil {
if !presentedViewController!.isBeingDismissed() {
self.dismissViewControllerAnimated(false, completion: {
navC.pushViewController(portraitVC, animated: true)
})
}
} else {
navC.pushViewController(portraitVC, animated: true)
}
}
这些警告或错误的原因是,在关闭和呈现视图控制器时存在延迟,并且您呈现和关闭的调用彼此重叠。
第一个错误报告该视图不在层次结构中,这意味着您试图在原来的视图控制器或导航控制器上显示一个视图,该视图不再可用,因为已模态地显示了另一个视图控制器。
与在取消分配视图时加载视图有关的第二个错误指示,当尝试进行另一个模式表示时,视图控制器的解除还没有完全完成。
为防止这些问题,需要在提交新的视图控制器之前确保撤消已完成。 这可以通过在dismiss方法中使用完成处理程序处理状态并在isBeingDismissed
状态上添加检查来实现。
这是一些实现此目的的代码:
override func viewWillTransitionToSize(size: CGSize, withTransitionCoordinator coordinator: UIViewControllerTransitionCoordinator) {
super.viewWillTransitionToSize(size, withTransitionCoordinator: coordinator)
let storyboard = UIStoryboard(name: "Main", bundle: nil)
if UIDeviceOrientationIsLandscape(UIDevice.currentDevice().orientation) {
let landscapeVC = storyboard.instantiateViewControllerWithIdentifier("landscapeViewController") as! beerCollectionViewController
if presentedViewController != nil {
if !presentedViewController!.isBeingDismissed() {
dismissViewControllerAnimated(false, completion: {
self.presentViewController(landscapeVC!, animated: true, completion: nil)
})
}
} else {
self.presentViewController(landscapeVC!, animated: true, completion: nil)
}
} else { // Portrait
let portraitVC = storyboard.instantiateViewControllerWithIdentifier("portraitViewController") as! ViewController
if presentedViewController != nil {
if !presentedViewController!.isBeingDismissed() {
dismissViewControllerAnimated(false, completion: {
self.presentViewController(portraitVC!, animated: true, completion: nil)
})
}
} else {
self.presentViewController(portraitVC!, animated: true, completion: nil)
}
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.