UISplitViewController - 防止在 iPhone 6 plus 上横向拆分
UISplitViewController - prevent splitting in landscape on iPhone 6 plus
我在我的应用程序中使用 UISplitViewController。这在 iPad 上工作得很好,其中主要和次要始终可见,并且在大多数 iPhone 上工作得很好,它就像一个 UINavigationController。
在 iPhone 6+ 和 6S+ 上,拆分视图在纵向中的作用类似于 iPhone,在横向中的作用类似于 iPad。这种景观分裂给我带来了问题,我想避免它。
有什么方法可以防止 UISplitViewController 在 iPhone 6+ 横向中显示主控制器和辅助控制器?我只是想让它显示辅助控制器,就像它对其他 iPhones 所做的一样。
谢谢。
我能够通过子classing UISplitViewController 然后将特征集合覆盖到 return 紧凑的水平尺寸 class 当设备不是 iPad。我知道现在检查界面惯用语是一种失礼,但我不确定该怎么做。
我只是将这个方法添加到我的 UISplitViewController subclass:
-(UITraitCollection *)traitCollection {
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
return [super traitCollection];
} else {
return [UITraitCollection traitCollectionWithHorizontalSizeClass:UIUserInterfaceSizeClassCompact];
}
}
当然欢迎任何关于更好的方法的建议。
这里是 Swift 中的相同答案,但还修复了垂直尺寸 class 在横向 phone 上错误的问题:
override var traitCollection: UITraitCollection {
if UI_USER_INTERFACE_IDIOM() == .pad {
return super.traitCollection
} else {
let horizontal = UITraitCollection(horizontalSizeClass: .compact)
let vertical = UITraitCollection(verticalSizeClass: super.traitCollection.verticalSizeClass)
return UITraitCollection.init(traitsFrom: [horizontal, vertical])
}
}
我遇到了一些问题,UINavigationControllers 无法通过上面的代码正确显示。这是对我有用的方法 (Swift 5):
1) 创建一个包含 UIContainerView 的 UIViewController
2) 在那个容器中嵌入你的 UISplitViewController
3) 添加以下代码:
class SplitViewContainerViewController: 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)
}
}
}
4) 设置包含容器视图的视图控制器为SplitViewContainerViewController
更新 iOS 13
上面的代码不再适用于 iOS 13. 在 SplitViewContainerViewController class 上改用以下代码:
override func overrideTraitCollection(forChild childViewController: UIViewController) -> UITraitCollection? {
if UIDevice.current.userInterfaceIdiom != .pad {
return UITraitCollection(horizontalSizeClass: .compact)
} else {
return super.traitCollection
}
}
我在我的应用程序中使用 UISplitViewController。这在 iPad 上工作得很好,其中主要和次要始终可见,并且在大多数 iPhone 上工作得很好,它就像一个 UINavigationController。
在 iPhone 6+ 和 6S+ 上,拆分视图在纵向中的作用类似于 iPhone,在横向中的作用类似于 iPad。这种景观分裂给我带来了问题,我想避免它。
有什么方法可以防止 UISplitViewController 在 iPhone 6+ 横向中显示主控制器和辅助控制器?我只是想让它显示辅助控制器,就像它对其他 iPhones 所做的一样。
谢谢。
我能够通过子classing UISplitViewController 然后将特征集合覆盖到 return 紧凑的水平尺寸 class 当设备不是 iPad。我知道现在检查界面惯用语是一种失礼,但我不确定该怎么做。
我只是将这个方法添加到我的 UISplitViewController subclass:
-(UITraitCollection *)traitCollection {
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
return [super traitCollection];
} else {
return [UITraitCollection traitCollectionWithHorizontalSizeClass:UIUserInterfaceSizeClassCompact];
}
}
当然欢迎任何关于更好的方法的建议。
这里是 Swift 中的相同答案,但还修复了垂直尺寸 class 在横向 phone 上错误的问题:
override var traitCollection: UITraitCollection {
if UI_USER_INTERFACE_IDIOM() == .pad {
return super.traitCollection
} else {
let horizontal = UITraitCollection(horizontalSizeClass: .compact)
let vertical = UITraitCollection(verticalSizeClass: super.traitCollection.verticalSizeClass)
return UITraitCollection.init(traitsFrom: [horizontal, vertical])
}
}
我遇到了一些问题,UINavigationControllers 无法通过上面的代码正确显示。这是对我有用的方法 (Swift 5):
1) 创建一个包含 UIContainerView 的 UIViewController
2) 在那个容器中嵌入你的 UISplitViewController
3) 添加以下代码:
class SplitViewContainerViewController: 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)
}
}
}
4) 设置包含容器视图的视图控制器为SplitViewContainerViewController
更新 iOS 13
上面的代码不再适用于 iOS 13. 在 SplitViewContainerViewController class 上改用以下代码:
override func overrideTraitCollection(forChild childViewController: UIViewController) -> UITraitCollection? {
if UIDevice.current.userInterfaceIdiom != .pad {
return UITraitCollection(horizontalSizeClass: .compact)
} else {
return super.traitCollection
}
}