关于iOS16 以后屏幕旋转不得不说的事

由于笔者最近刚完成了一个强制屏幕横屏的需求 所以 顺便记录一下 实现过程中遇到 block点 也为广大的iOS开发者做一个笔记:

废话不多说直接上代码

 //适配iOS16.0的横竖屏方法
    public static func switchInterfaceWtihIos16(orientation: UIInterfaceOrientation , orientationMask: UIInterfaceOrientationMask) {
    
    
        if #available(iOS 16.0, *) {
    
    
            let array = UIApplication.shared.connectedScenes
            let geometryPreferencesIOS = UIWindowScene.GeometryPreferences.iOS(interfaceOrientations: orientationMask)
            if  let scene = array.first as? UIWindowScene {
    
    
                UIViewController.attemptRotationToDeviceOrientation()
                SystemManager.currentViewController()?.setNeedsUpdateOfSupportedInterfaceOrientations()
                scene.requestGeometryUpdate(geometryPreferencesIOS) {
    
     e in
                    log.info("iOS16 屏幕旋转失败:error \(e)")
                    scene.requestGeometryUpdate(geometryPreferencesIOS)
                }
            }

        } else {
    
    
            let resetOrientationTarget = NSNumber(value: UIInterfaceOrientation.unknown.rawValue)
            UIDevice.current.setValue(resetOrientationTarget, forKey: "orientation")
            let orientationTarget = NSNumber(value: orientation.rawValue)
            UIDevice.current.setValue(orientationTarget, forKey: "orientation")
        }
    }

值得一提的是 iOS16以后新增了GeometryPreferences 方法来旋转屏幕,所以设置横竖屏需要 使用的新的方法,并且入参为 UIInterfaceOrientationMask

调用上述方法以后 还要在需要实现横屏controller重写下面的方法和属性

    // 是否支持旋转
    open override var shouldAutorotate: Bool {
    
    
        return false
    }
    
    // 支持的方向
    open override var supportedInterfaceOrientations: UIInterfaceOrientationMask {
    
    
        return .landscapeRight
    }
    // 首次展示的方向
    open override var preferredInterfaceOrientationForPresentation: UIInterfaceOrientation {
    
    
        return  .landscapeRight
    }
    @available(iOS 16.0, *)
    public override func setNeedsUpdateOfSupportedInterfaceOrientations() {
    
    
        let orientation = UIDevice.current.orientation
        if orientation == .landscapeLeft || orientation == .landscapeRight || orientation == .faceUp || orientation == .faceDown || isLandScreen {
    
    
            player.setfullScreen(isFull: true)
        } else {
    
    
            player.setfullScreen(isFull: false)
        }
    }

islandscreen 是我用来判断是否横屏的一个bool,直接复制可能会报错。大家复制后删除该判断再根据实际情况去修改就好

接下来着重说明一下 setNeedsUpdateOfSupportedInterfaceOrientations ,
这个是iOS16以后 的一个新方法,它的作用就是 每当屏幕旋转就会进入这个回调方法。当然你也可以主动调用,正如开篇方法中SystemManager.currentViewController()?.setNeedsUpdateOfSupportedInterfaceOrientations()
它的作用就是主动进入该方法中 。

然后通过查阅其他博主文章,如果想要屏幕旋转正常还需要加上UIViewController.attemptRotationToDeviceOrientation()
下面是官方描述 :

Summary

Attempts to rotate all windows to the orientation of the device.

所以老铁加上没毛病
这里总结一下

  1. 新建一个工具类或者拓展,加入代码块一 内容
  2. 在需要横竖屏的controller,复制 代码块二 内容
  3. 然后如果你的项目之前还没有做过横竖屏的适配你还得请添加图片描述
    做截图相关配置。

猜你喜欢

转载自blog.csdn.net/lingjunjie/article/details/131300232