SceneDelegate
删除SceneDelegate
- 删除掉
info.plist
中Application Scene Manifest
选项,同时,文件SceneDelegate
可删除可不删 - 相关代码注释掉
Appdelegate
新增windows
属性
参考:
如果使用当前最新版本的Xcode新建项目,项目中会多出一个SceneDelegate.swift
的文件,并且AppDelegate.swift
的内容也会有所不同
AppDelegate.swift
的内容,可能如下:
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var openSessions: [String] = []
func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {
return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
}
}
先看下涉及的类
UISceneSession
UISceneSession管理scene的唯一运行时实例。 当用户向你的应用添加新scene时,或者当你以编程方式请求一个新scene时,系统会创建一个session会话对象来跟踪该scene。这个session包含一个唯一标识符和scene的配置(configuration)详细信息。 UIKit
在scene本身的生命周期内维护session信息,用户在应用程序切换器(app switcher)中关闭scene时,会销毁session
不需要直接创建session对象,UIKit
创建session以响应用户与你的应用程序的交互。你还可以通过调用UIApplication
的requestSceneSessionActivation(_:userActivity:options:errorHandler:)
方法来要求UIKit以编程方式创建新scene和session。 UIKit根据应用程序的Info.plist
文件的内容,使用默认配置数据初始化session。
UISceneConfiguration
UISceneConfiguration包含创建scene时所需要的必要信息。使用UISceneConfiguration
对象可以指定UIKit可以用来为你的应用创建新scene的信息。 具体来说,提供你想要的scene的class,scene的代理对象,和包含初始化控制器的storyboard。
当用户请求应用程序用户界面的新实例时,UIKit会在应用程序的Info.plist
文件中查找创建相应scene对象所需的配置数据。 然后,它将这些信息打包到一个UISceneConfiguration
对象中,并将其作为session的一部分,传递到app delegate的 application(_:configurationForConnecting:options:)
方法中,你可以按原样接受该配置数据,也可以创建一个具有不同配置详细信息集的新UISceneConfiguration
对象。
UIScene.ConnectionOptions
UIScene.ConnectionOptions是一个数据对象,包含有关UIKit
创建scene的原因的信息
UIKit创建scene的原因很多。它可能是为了响应切换请求或打开URL的请求而这样做的。 如果有创建scene的特定原因,则UIKit会将相关数据填充到UIScene.ConnectionOptions
对象中,并在连接时将其传递给你的委托。 使用此对象中的信息进行相应的响应。 例如,打开UIKit提供的URL,然后在scene中显示其内容。
不要直接创建UIScene.ConnectionOptions
对象。 UIKit为你创建UIScene.ConnectionOptions
对象,并将它们传递给scene委托的scene(_:willConnectTo:options:)
方法。
SceneDelegate.swift
内容如下
class SceneDelegate: UIResponder, UIWindowSceneDelegate {
var window: UIWindow?
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
if let windowScene = scene as? UIWindowScene {
let window = UIWindow(windowScene: windowScene)
window.rootViewController = UIHostingController(rootView: NoteListView())
self.window = window
window.makeKeyAndVisible()
}
}
}
UIScene
UIScene代表应用程序用户界面的一个实例的对象。
UIKit
为用户或应用程序请求时,为应用程序UI的每个实例创建一个scene对象。通常,UIKit
会创建UIWindowScene
对象而不是UIScene
对象,但是你可以使用此类的方法和属性来访问有关scene的信息。
每个scene对象都有一个关联的委托对象,该对象采用UISceneDelegate
协议。当scene的状态更改时,scene对象会通知其委托对象,并将适当的通知发布到已注册的观察者对象。使用委托对象和通知来响应scene状态的变化。例如,使用它来确定scene何时移至background。
你不直接创建scene对象。您可以通过调用UIApplication
的requestSceneSessionActivation(_:userActivity:options:errorHandler:)
方法以编程方式要求UIKit为您的应用创建scene对象。 UIKit还可以响应用户交互来创建scene。在配置应用程序的scene支持时,请指定UIWindowScene
对象而不是UIScene
对象。
UIWindowScene
class UIWindowScene : UIScene
UIWindowScene
是UIScene
的子类
UIWindowScene
对象管理应用程序UI的一个实例,包括从该scene显示的一个或多个窗口。scene对象管理窗口在用户设备上的显示以及该scene在用户与其交互时的生命周期。当scene的状态更改时,scene对象会通知其委托对象,该scene是采用UIWindowSceneDelegate
协议的对象。还会向注册观察者发布适当的通知。使用这些对象来响应任何更改。
下图显示了它们之间的关系
Multiple Scenes
如果app支持multiple-window,在向上滑动到app switcher时,会有app的多个window,可参考Introducing Multiple Windows on iPad中的介绍:
添加多Scene支持
1.在Info.plist
中将Enable Multiple Windows
设置为YES
当应用程序位于前台时,从底部向上滑动以启动dock。 点击并按住右侧的应用程序图标。 从菜单中选择“显示所有窗口”。 现在,将看到App Exposé 视图,并可以点击右上角的加号图标来启动新窗口:
当应用程序置于前台,向上滑动以再次显示dock。 这次,将应用程序图标拖出dock,直到它成为悬停窗口。 将窗口放在屏幕的右侧或左侧
在上一步的基础上,点击并按住窗口顶部的拖动手柄。 向下和向右拉,直到窗口改变形状。 将窗口放到屏幕的一侧,可以看到2个并排的窗口