[英]is Force View Controller Orientation working in iOS 16 beta
According to the iOS & iPadOS 16 Beta 3 Release Notes:- Attempting to set an orientation on UIDevice via setValue:forKey:
isn't supported and no longer works.根据 iOS 和 iPadOS 16 Beta 3 发行说明:- 尝试通过
setValue:forKey:
在UIDevice上设置方向不受支持且不再有效。 Instead, they say use: preferredInterfaceOrientationForPresentation.相反,他们说使用:preferredInterfaceOrientationForPresentation。
In my case, force view controller orientation is not working in iOS 16 beta either by using preferredInterfaceOrientationForPresentation
or requestGeometryUpdate
.就我而言,通过使用
preferredInterfaceOrientationForPresentation
或requestGeometryUpdate
强制视图控制器方向在 iOS 16 beta 中不起作用。
Previously, UIDevice.current.setValue(UIInterfaceOrientation.landscapeLeft.rawValue, forKey: "orientation")
was working fine.以前,
UIDevice.current.setValue(UIInterfaceOrientation.landscapeLeft.rawValue, forKey: "orientation")
工作正常。
It works for me:这个对我有用:
import Foundation
import UIKit
extension UIViewController {
func setDeviceOrientation(orientation: UIInterfaceOrientationMask) {
if #available(iOS 16.0, *) {
let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene
windowScene?.requestGeometryUpdate(.iOS(interfaceOrientations: orientation))
} else {
UIDevice.current.setValue(orientation.toUIInterfaceOrientation.rawValue, forKey: "orientation")
}
}
}
extension UIInterfaceOrientationMask {
var toUIInterfaceOrientation: UIInterfaceOrientation {
switch self {
case .portrait:
return UIInterfaceOrientation.portrait
case .portraitUpsideDown:
return UIInterfaceOrientation.portraitUpsideDown
case .landscapeRight:
return UIInterfaceOrientation.landscapeRight
case .landscapeLeft:
return UIInterfaceOrientation.landscapeLeft
default:
return UIInterfaceOrientation.unknown
}
}
}
How to use it?如何使用它?
Just call it on your UIViewController:只需在您的 UIViewController 上调用它:
setDeviceOrientation(orientation: .landscapeRight)
EDIT编辑
More completed solution:更完整的解决方案:
import UIKit
final class DeviceOrientation {
static let shared: DeviceOrientation = DeviceOrientation()
// MARK: - Private methods
private var windowScene: UIWindowScene? {
return UIApplication.shared.connectedScenes.first as? UIWindowScene
}
// MARK: - Public methods
func set(orientation: UIInterfaceOrientationMask) {
if #available(iOS 16.0, *) {
windowScene?.requestGeometryUpdate(.iOS(interfaceOrientations: orientation))
} else {
UIDevice.current.setValue(orientation.toUIInterfaceOrientation.rawValue, forKey: "orientation")
}
}
var isLandscape: Bool {
if #available(iOS 16.0, *) {
return windowScene?.interfaceOrientation.isLandscape ?? false
}
return UIDevice.current.orientation.isLandscape
}
var isPortrait: Bool {
if #available(iOS 16.0, *) {
return windowScene?.interfaceOrientation.isPortrait ?? false
}
return UIDevice.current.orientation.isPortrait
}
var isFlat: Bool {
if #available(iOS 16.0, *) {
return false
}
return UIDevice.current.orientation.isFlat
}
}
extension UIInterfaceOrientationMask {
var toUIInterfaceOrientation: UIInterfaceOrientation {
switch self {
case .portrait:
return UIInterfaceOrientation.portrait
case .portraitUpsideDown:
return UIInterfaceOrientation.portraitUpsideDown
case .landscapeRight:
return UIInterfaceOrientation.landscapeRight
case .landscapeLeft:
return UIInterfaceOrientation.landscapeLeft
default:
return UIInterfaceOrientation.unknown
}
}
}
How to use it:如何使用它:
DeviceOrientation.shared.set(orientation: .portrait)
I noticed my issue seems like resolved by calling method below:我注意到我的问题似乎可以通过调用以下方法解决:
[UIViewController setNeedsUpdateOfSupportedInterface [UIViewController setNeedsUpdateOfSupportedInterface
You may give it a try.你可以试一试。
setValue:forKey
is a method of old NSObject
( NSKeyValueCoding
). setValue:forKey
是旧NSObject
( NSKeyValueCoding
) 的方法。 It's not official documented and supported by UIDevice
class. UIDevice
class 没有官方记录和支持。 Using it is considering using a private api.使用它正在考虑使用私有 api。 Apple can terminate it anytime they want.
苹果可以随时终止它。
My problem with my code below is that I'm trying to do it when closing a modal view and the view under it are not updated quick enough.我在下面的代码中遇到的问题是,我在关闭模态视图时尝试这样做,而它下面的视图更新得不够快。 If I put the requestGeometryUpdate on a separate button then when I close the view it work.
如果我将 requestGeometryUpdate 放在一个单独的按钮上,那么当我关闭视图时它就会起作用。
if #available(iOS 16.0, *) {
let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene
windowScene?.requestGeometryUpdate(.iOS(interfaceOrientations: .portrait))
}
Apple released new API which is replaced with setValue:forKey:"orientation". Apple 发布了新的 API 替换为 setValue:forKey:"orientation"。 Apple update
苹果更新
guard let windowScene = view.window?.windowScene else { return }
windowScene.requestGeometryUpdate(.iOS(interfaceOrientations: .landscape)) { error in
// Handle denial of request.
}
But I am having problem about UIDevice.orientationDidChangeNotification
, it is not working但我对
UIDevice.orientationDidChangeNotification
有问题,它不工作
It works for me.这个对我有用。
In AppDelegate,在 AppDelegate 中,
var orientation: UIInterfaceOrientationMask = .portrait
func application(_ application: UIApplication, supportedInterfaceOrientationsFor window: UIWindow?) -> UIInterfaceOrientationMask {
return orientation
}
In view controller,鉴于controller,
(UIApplication.shared.delegate as? AppDelegate)?.orientation = .landscapeRight
let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene
windowScene?.requestGeometryUpdate(.iOS(interfaceOrientations: .landscapeRight))
UIApplication.navigationTopViewController()?.setNeedsUpdateOfSupportedInterfaceOrientations()
Following Apple's documentation you need to按照 Apple 的文档,您需要
Requests an update to the window scene's geometry using the specified geometry preferences object.
使用指定的几何首选项对象请求更新窗口场景的几何图形。
https://developer.apple.com/documentation/uikit/uiwindowscene/3975944-requestgeometryupdate/ https://developer.apple.com/documentation/uikit/uiwindowscene/3975944-requestgeometryupdate/
So using the code in the example, you can change the way we set the orientation in our views using requestGeometryUpdate
and using as well setNeedsUpdateOFSupportedInterface
因此,使用示例中的代码,您可以使用
requestGeometryUpdate
和setNeedsUpdateOFSupportedInterface
更改我们在视图中设置方向的方式
public extension UIViewController {
func deviceOrientation(orientation: UIInterfaceOrientationMask) {
if #available(iOS 16.0, *) {
guard let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene
else { return }
windowScene.requestGeometryUpdate(.iOS(interfaceOrientations: orientation))
self.setNeedsUpdateOfSupportedInterfaceOrientations()
}
}
}
I tried all above solutions seem they're not 100% percent working.我尝试了以上所有解决方案,但它们似乎并非 100% 有效。 After through this post https://developer.apple.com/forums/thread/707735 i got the hint.
通过这篇文章https://developer.apple.com/forums/thread/707735我得到了提示。 Let's try this below code.
让我们试试下面的代码。 It's worked for me.
它对我有用。
if #available(iOS 16.0, *) {
DispatchQueue.main.async {
UIViewController.attemptRotationToDeviceOrientation()
let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene
windowScene?.requestGeometryUpdate(.iOS(interfaceOrientations: orientation)) { error in
print(error)
print(windowScene?.effectiveGeometry)
}
navigationController?.topViewController?.setNeedsUpdateOfSupportedInterfaceOrientations()
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.