![](/img/trans.png)
[英]Xcode 12 project with iOS 13 SwiftUI support: SceneDelegate functions not invoked
[英]AppDelegate and SceneDelegate when supporting iOS 12 and 13
我需要支持 iOS 12 和 iOS 13。
我應該在AppDelegate
和SceneDelegate
之間復制代碼嗎?
例如:
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
guard let windowScene = (scene as? UIWindowScene) else { return }
let window = UIWindow(windowScene: windowScene)
window.rootViewController = HomeViewController()
window.makeKeyAndVisible()
self.window = window
}
和
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
let window = UIWindow(frame: UIScreen.main.bounds)
window.rootViewController = HomeViewController()
window.makeKeyAndVisible()
self.window = window
return true
}
如果我不這樣做,在 1 版本中我最終會出現黑屏,但如果我這樣做並在HomeViewController
的viewDidLoad
方法中打印,我可以看到它被調用了兩次。
我更新了我的didFinishLaunchingWithOptions
並且我可以在iOS13
中看到它仍然被調用了兩次。
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
guard #available(iOS 12, *) else { return true }
let window = UIWindow(frame: UIScreen.main.bounds)
window.rootViewController = HomeViewController()
window.makeKeyAndVisible()
self.window = window
return true
}
您確實需要復制代碼,但您需要確保它僅在正確的系統上運行。 在 iOS 13 中,您不希望應用程序委托didFinishLaunching
主體代碼運行,因此使用可用性檢查來阻止它。 同樣,使用可用性從 iOS 12 中隱藏 window 場景內容。
這是在 iOS 12 和 iOS 13 上正確運行的解決方案的基本草圖:
import UIKit
@UIApplicationMain
class AppDelegate : UIResponder, UIApplicationDelegate {
var window : UIWindow?
func application(_ application: UIApplication,
didFinishLaunchingWithOptions
launchOptions: [UIApplication.LaunchOptionsKey : Any]?)
-> Bool {
if #available(iOS 13, *) {
// do only pure app launch stuff, not interface stuff
} else {
self.window = UIWindow()
let vc = ViewController()
self.window!.rootViewController = vc
self.window!.makeKeyAndVisible()
self.window!.backgroundColor = .red
}
return true
}
}
import UIKit
@available(iOS 13.0, *)
class SceneDelegate: UIResponder, UIWindowSceneDelegate {
var window : UIWindow?
func scene(_ scene: UIScene,
willConnectTo session: UISceneSession,
options connectionOptions: UIScene.ConnectionOptions) {
if let windowScene = scene as? UIWindowScene {
self.window = UIWindow(windowScene: windowScene)
let vc = ViewController()
self.window!.rootViewController = vc
self.window!.makeKeyAndVisible()
self.window!.backgroundColor = .red
}
}
}
import UIKit
class ViewController : UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
print("view did load")
self.view.backgroundColor = .green
}
}
請注意,處理其他重復項(例如應用程序激活)要簡單得多,因為如果您支持 window 場景,則不會在 iOS 12 上調用應用程序委托方法。所以問題僅限於這種情況,即您有 Z05B8C735296FBF2FZDE4C1 / 根視圖 controller 在啟動時執行的操作(例如,沒有情節提要)。
Xcode 11.* 和 Swift 5.*
按照下面給出的步驟,您的代碼將適用於 iOS 12 和 iOS 13 -
希望這對某人有用。 快樂編碼
這是我的工作。
@提供了 SceneDelegate.swift
As the SceneDelegate class is only available on iOS 13 and above, we have to tell the compiler to only include the class for iOS 13 and above. 為此,我們將在 SceneDelegate class 聲明的正上方添加這一行“@available(iOS 13.0, *)”,如下所示:
import UIKit
@available(iOS 13.0, *)
class SceneDelegate: UIResponder, UIWindowSceneDelegate {
//...
}
@在 AppDelegate.swift 中提供一些方法
接下來在AppDelegate.swift中新增兩個方法,僅支持iOS 13及以上。 我們還將在它們之上添加相同的 @available(iOS 13.0, *) :
// AppDelegate.swift
@available(iOS 13.0, *)
func application(_ application: UIApplication, configurationForConnecting connectingSceneSession: UISceneSession, options: UIScene.ConnectionOptions) -> UISceneConfiguration {
// Called when a new scene session is being created.
// Use this method to select a configuration to create the new scene with.
return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
}
@available(iOS 13.0, *)
func application(_ application: UIApplication, didDiscardSceneSessions sceneSessions: Set<UISceneSession>) {
// 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.
}
將 window 添加回 AppDelegate
如果您現在構建並運行您的應用程序,您將看到黑屏,因為沒有初始化 UIWindow。
在 iOS 12 和更早版本中,總是有一個 var window: UIWindow? 位於 AppDelegate.swft 頂部的變量。 iOS 13 已將此變量移至 SceneDelegate.swift,現在我們將將此變量添加回 AppDelegate。
import UIKit
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
// ...
}
現在在 iOS 12 設備上構建並運行您的應用程序,它可以工作了!
I guess Apple really wants iOS developers to adopt and focus on iOS 13, to the extent that they don't mind breaking support for iOS 12 and older with default settings in Xcode.
If you are lazy to do these step manually every time, you can also download Xcode 10.3 in the Apple's developer download portal (require sign in with your Apple ID), create a new Xcode project using it, and then edit it using Xcode 11.
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.