在SwiftUI中实现外部监视器支持 [英] Implementing external monitor support in SwiftUI

查看:125
本文介绍了在SwiftUI中实现外部监视器支持的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对于通过Airplay和SwiftUI实现外部显示器支持感到困惑.

I'm confused about implementing external monitor support via Airplay with SwiftUI.

在SceneDelegate.swift中,我使用的是UIScreen.didConnectNotification观察器,它实际上检测到已附加新屏幕,但是无法为该屏幕分配自定义UIScene.

In SceneDelegate.swift I'm using UIScreen.didConnectNotification observer and it actually detects a new screen being attached but I'm unable to assign a custom UIScene to the screen.

我发现了一些在iOS12及更低版本上使用Swift的好示例,但是它们都不能在SwiftUI中使用,因为整个范例已更改为使用UIScene而不是UIScreen.这是列表:

I found a few good examples using Swift with iOS12 and lower, but none of them work in SwiftUI, since the whole paradigm has been changed to use UIScene instead of UIScreen. Here's the list:

https ://www.bignerdranch.com/blog/adding-external-display-support-to-your-ios-app-is-ridiculously-easy/

https://developer.apple.com/documentation/uikit/windows_and_screens/displaying_content_on_a_connected_screen

https://www.swiftjectivec.com/supporting-external-displays/

苹果甚至去年也对此发表了看法

也许某些事情发生了变化,现在有一种新方法可以正确执行此操作. 此外,iOS13中已弃用设置UIWindow.screen = screen.

Perhaps something changed and now there is a new way to do this properly. Moreover, setting UIWindow.screen = screen has been deprecated in iOS13.

任何人都已经尝试过使用SwiftUI实现外部屏幕支持.非常感谢您的帮助.

Has anyone already tried implementing an external screen support with SwiftUI. Any help is much appreciated.

推荐答案

我修改了Big Nerd Ranch博客中的示例,使其工作如下.

I modified the example from the Big Nerd Ranch blog to work as follows.

  1. 删除主情节提要:我从一个新项目中删除了主情节提要.在部署信息下,我将Main接口设置为一个空字符串.

  1. Remove Main Storyboard: I removed the main storyboard from a new project. Under deployment info, I set Main interface to an empty string.

编辑plist:在plist的应用程序场景清单"部分中定义两个场景(默认和外部)及其场景委托.

Editing plist: Define your two scenes (Default and External) and their Scene Delegates in the Application Scene Manifest section of your plist.

    <key>UIApplicationSceneManifest</key>
    <dict>
        <key>UIApplicationSupportsMultipleScenes</key>
        <true/>
        <key>UISceneConfigurations</key>
        <dict>
            <key>UIWindowSceneSessionRoleApplication</key>
            <array>
                <dict>
                    <key>UISceneConfigurationName</key>
                    <string>Default Configuration</string>
                    <key>UISceneDelegateClassName</key>
                    <string>$(PRODUCT_MODULE_NAME).SceneDelegate</string>
                </dict>
            </array>
            <key>UIWindowSceneSessionRoleExternalDisplay</key>
            <array>
                <dict>
                    <key>UISceneDelegateClassName</key>
                    <string>$(PRODUCT_MODULE_NAME).ExtSceneDelegate</string>
                    <key>UISceneConfigurationName</key>
                    <string>External Configuration</string>
                </dict>
            </array>
        </dict>
    </dict>

  1. 编辑视图控制器以显示简单的字符串:

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()
        view.backgroundColor = .blue
        view.addSubview(screenLabel)
    }

    var screenLabel: UILabel = {
        let label = UILabel()
        label.textColor = UIColor.white
        label.font = UIFont(name: "Helvetica-Bold", size: 22)
        return label
    }()

    override func viewDidLayoutSubviews() {
        /* Set the frame when the layout is changed */
        screenLabel.frame = CGRect(x: 0,
                                y: 0,
                                width: view.frame.width - 30,
                                height: 24)
    }
}

  1. 在SceneDelegate中修改场景(_:willConnectTo:options :)以在主(iPad)窗口中显示信息.

    func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
        // Use this method to optionally configure and attach the UIWindow `window` to the provided UIWindowScene `scene`.
        // If using a storyboard, the `window` property will automatically be initialized and attached to the scene.
        // This delegate does not imply the connecting scene or session are new (see `application:configurationForConnectingSceneSession` instead).
        guard let windowScene = (scene as? UIWindowScene) else { return }

        window = UIWindow(frame: windowScene.coordinateSpace.bounds)
        window?.windowScene = windowScene
        let vc = ViewController()
        vc.loadViewIfNeeded()
        vc.screenLabel.text = String(describing: window)
        window?.rootViewController = vc
        window?.makeKeyAndVisible()
        window?.isHidden = false
    }

  1. 为您的外部屏幕创建场景委托.我制作了一个新的Swift文件ExtSceneDelegate.swift,其中包含与SceneDelegate.swift相同的文本,将类的名称从SceneDelegate更改为ExtSceneDelegate.

  1. Make a scene delegate for your external screen. I made a new Swift file ExtSceneDelegate.swift that contained the same text as SceneDelegate.swift, changing the name of the class from SceneDelegate to ExtSceneDelegate.

在AppDelegate中修改应用程序(_:configurationForConnecting:options :).其他人则建议,如果您仅对此发表评论,一切都会好起来的.对于调试,我发现将其更改为:

Modify application(_:configurationForConnecting:options:) in AppDelegate. Others have suggested that everything will be fine if you just comment this out. For debugging, I found it helpful to change it to:

    func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {

        // This is not necessary; however, I found it useful for debugging
        switch connectingSceneSession.role.rawValue {
            case "UIWindowSceneSessionRoleApplication":
                return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
            case "UIWindowSceneSessionRoleExternalDisplay":
                return UISceneConfiguration(name: "External Configuration", sessionRole: connectingSceneSession.role)
            default:
                fatalError("Unknown Configuration \(connectingSceneSession.role.rawValue)")
            }
    }

  1. 在iOS上构建并运行该应用.您应该会看到一个丑陋的蓝屏,上面写有有关UIWindow的信息.然后,我使用屏幕镜像连接到Apple TV.您应该会在外部屏幕上看到类似的丑陋蓝色屏幕,其中包含不同的UIWindow信息.

对我来说,解决所有问题的关键参考是 https://onmyway133.github.io/blog/How-to-use-external-display-in-iOS/.

For me, the key reference for figuring all of this out was https://onmyway133.github.io/blog/How-to-use-external-display-in-iOS/.

这篇关于在SwiftUI中实现外部监视器支持的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆