问题
In a Universal App I can't find a way to always show (and only) the master controller, even on iPhone 6 Plus in landscape rotation.
What I want to achieve is to see UISplitViewController in action only on the iPad and NOT on the iPhone, don't know if it's possible
delegate methods doesn't help:
func splitViewController(svc: UISplitViewController, shouldHideViewController vc: UIViewController, inOrientation orientation: UIInterfaceOrientation) -> Bool {
return false
}
func splitViewController(splitViewController: UISplitViewController, collapseSecondaryViewController secondaryViewController: UIViewController, ontoPrimaryViewController primaryViewController: UIViewController) -> Bool {
return true
}
回答1:
You need to override the trait collection of your UISplitViewController to always have a compact size class. To do so you need to insert a container view controller as the parent of your UISplitViewController:
- Embed your UISplitViewController into a ContainerViewController
Add the following code into your container view controller subclass to override the trait collection of your child view controller:
class ContainerVC: UIViewController { override func viewDidLoad() { super.viewDidLoad() } override func viewWillTransitionToSize(size: CGSize, withTransitionCoordinator coordinator: UIViewControllerTransitionCoordinator) { performOverrideTraitCollection() } private func performOverrideTraitCollection() { for childVC in self.childViewControllers { setOverrideTraitCollection(UITraitCollection(horizontalSizeClass: .Compact), forChildViewController: childVC) } }}
Great explanation in Building Adaptive Apps with UIKit (WWDC 2014)
回答2:
Terry's answer works great! Here it is updated to Swift 5 and to work only on iPhone devices, not iPad:
class ContainerVC: UIViewController {
override func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
if UI_USER_INTERFACE_IDIOM() != .pad {
performOverrideTraitCollection()
}
}
private func performOverrideTraitCollection() {
for childVC in self.children {
setOverrideTraitCollection(UITraitCollection(horizontalSizeClass: .compact), forChild: childVC)
}
}
}
Update For iOS 13
The code above no longer works on iOS 13. Use the following instead in the ContainerVC class:
override func overrideTraitCollection(forChild childViewController: UIViewController) -> UITraitCollection? {
if UIDevice.current.userInterfaceIdiom != .pad {
return UITraitCollection(horizontalSizeClass: .compact)
} else {
return super.traitCollection
}
}
来源:https://stackoverflow.com/questions/35705865/force-uisplitviewcontroller-to-always-show-master-only-in-landscape-on-iphone