xcode11創建項目新增SceneDelegate文件,AppDelegate文件結構也發生變化,在AppDelegate.h文件中沒有了window屬性,而是在SceneDelegate.h中,可見AppDelegate不管理window而是交給SceneDelegate。由于這些是ios13新增,所以SceneDelegate在ios13以下的系統是不支持。所以xcode11創建的項目如要做一下處理:
如果App不需要支持多個scene,同時兼容ios13以下,可以刪除info.plist文件中的Application Scene Manifest的配置數據。在AppDelegate.h中添加window屬性,同時刪除UISceneSession的生命周期方法。和以前的使用方式一樣??蓞⒖?a href="http://www.lxweimin.com/p/49c6770a94e0" target="_blank">iOS移除SceneDelegate
如果在ios13中支持多scene,原先AppDelegate的生命周期方法不再起作用。
而是在SceneDelegate中使用UIScene提供的生命周期方法
開啟支持多scene(僅iPad有效)
image.png
由于勾選分屏,在info.plist 中 Application Scene Manifest
-> enable Multipe Windows
設置為YES.
image.png
默認在info.plist中進行了配置, 不用實現該方法也沒有關系。如果沒有配置就需要實現這個方法并返回一個UISceneConfiguration對象。
在上圖中配置參數中Application Session Role 是個數組,每一項有三個參數,
Configuration Name: 當前配置的名字
Delegate Class Name: 與哪個Scene代理對象關聯,
StoryBoard name: 這個Scene使用的哪個storyboard。
AppDelegate.m中多了UISceneSession的生命周期的代理方法
//1.如果沒有在APP的Info.plist文件中包含scene的配置數據,或者要動態更改場景配置數據,需要實現此方法。 UIKit會在創建新scene前調用此方法。
//參數options是一個UISceneConnectionOptions類,官方解釋:它包含了為什么要創建一個新的scene的信息。根據參數信息判斷是否要創建一個新的scene
- (UISceneConfiguration *)application:(UIApplication *)application configurationForConnectingSceneSession:(UISceneSession *)connectingSceneSession options:(UISceneConnectionOptions *)options {
NSLog(@"1");
// Called when a new scene session is being created.
// Use this method to select a configuration to create the new scene with.
return [[UISceneConfiguration alloc] initWithName:@"Default Configuration" sessionRole:connectingSceneSession.role];
}
//方法會返回一個UISceneConfiguration對象,其包含其中包含場景詳細信息,包括要創建的場景類型,用于管理場景的委托對象以及包含要顯示的初始視圖控制器的情節提要。 如果未實現此方法,則必須在應用程序的Info.plist文件中提供場景配置數據。
//總結下:默認在info.plist中進行了配置, 不用實現該方法也沒有關系。如果沒有配置就需要實現這個方法并返回一個UISceneConfiguration對象。
//在分屏中關閉其中一個或多個scene時候回調用。
- (void)application:(UIApplication *)application didDiscardSceneSessions:(NSSet<UISceneSession *> *)sceneSessions {
// Called when the user discards a scene session.
// If any sessions were discarded while the application was not running, this will be called shortly after application:didFinishLaunchingWithOptions.
// Use this method to release any resources that were specific to the discarded scenes, as they will not return.
NSLog(@"2");
}
在SceneDelegate中不使用storyboard創建,手動創建新的window
- (void)scene:(UIScene *)scene willConnectToSession:(UISceneSession *)session options:(UISceneConnectionOptions *)connectionOptions {
//在這里手動創建新的window
if (scene) {
UIWindowScene *windowScene = (UIWindowScene *)scene;
self.window = [[UIWindow alloc] initWithWindowScene:windowScene];
self.window.frame = CGRectMake(0, 0, [UIScreen mainScreen].bounds.size.width, [UIScreen mainScreen].bounds.size.height);
self.window.rootViewController = [ViewController new];
[self.window makeKeyAndVisible];
}
}
SceneDelegate生命周期
- (void)scene:(UIScene *)scene willConnectToSession:(UISceneSession *)session options:(UISceneConnectionOptions *)connectionOptions {
NSLog(@"場景加載完成");
}
- (void)sceneDidDisconnect:(UIScene *)scene {
NSLog(@"場景已經斷開連接");
}
- (void)sceneDidBecomeActive:(UIScene *)scene {
NSLog(@"已經從后臺進入前臺");
}
- (void)sceneWillResignActive:(UIScene *)scene {
NSLog(@"即將從前臺進入后臺");
}
- (void)sceneWillEnterForeground:(UIScene *)scene {
NSLog(@"即將從后臺進入前臺");
}
- (void)sceneDidEnterBackground:(UIScene *)scene {
NSLog(@"已經從前臺進入后臺");
}