是否可以迁移旧的 Xcode 项目以使用 SwiftUI?
Is it possible to migrate an old Xcode project to use SwiftUI?
我有一个使用 Main.storyboard 在 Xcode 10 中制作的应用程序,我想将其迁移以使用 Apple 的新框架:SwiftUI。
已经可以了吗?
我已经尝试在 Info.plist
中添加 UIApplicationSceneManifest
键,我将 AppDelegate.swift
更改为使用场景,我创建了 SceneDelegate.swift
即使这样我也可以不是
我假设您使用的是 Xcode 11 GM
和 macOS Mojave
或 Catalina
。
随着 plist
中的更改,您必须在应用程序委托中添加 UISceneSession
生命周期函数。
func application(_ application: UIApplication,
configurationForConnecting connectingSceneSession: UISceneSession,
options: UIScene.ConnectionOptions) -> UISceneConfiguration {
// The name must match the one in the Info.plist
return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
}
func application(_ application: UIApplication, didDiscardSceneSessions sceneSessions: Set<UISceneSession>) {
}
此外,您需要确保 window
在 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 = UIHostingController(rootView: ContentView())
self.window = window
window.makeKeyAndVisible()
}
其中 ContentView
是您要显示的主要 SwiftUI
视图。
P.S。确保 plist
指定 $(PRODUCT_MODULE_NAME).SceneDelegate
作为委托 class 名称,场景委托称为 SceneDelegate
示例:
如果您使用 Catalina
,您可以在目标的构建设置中打开 Previews
。
构建选项 -> 启用预览
附录 I:
确保从 Info.Plist 和 you're targeting iOS 13
.
中删除 Storyboard 键
附录二:
清洁 Derived Data
,正如评论中的许多开发者所建议的那样。
我的解决方案原来是不同的。在我的例子中,我已经准备好了一切,但是当代码试图加载 UISceneConfiguration
时,它无法加载 Info.plist
中的配置,而是给了我一个辅助 window 配置没有设置场景委托。如果我从调试控制台请求正确的配置,它将按预期加载。我一头雾水。
我仔细检查了所有内容并尝试了此处的所有建议,但 none 奏效了。最后我在模拟器上做了 'Hardware' - 'Erase all contents and settings...' 并解决了它。
我的猜测是,因为我在模拟器上使用的是 运行 应用程序的 pre-SwiftUI 版本,所以其中的某些内容导致 SwiftUI 版本的行为有所不同。
这是一个正确的小改动
在SceneDelegate.swift
中替换
let window = UIWindow(frame: UIScreen.main.bounds)
window.rootViewController = UIHostingController(rootView: ContentView())
self.window = window
window.makeKeyAndVisible()
和
if let windowScene = scene as? UIWindowScene {
let window = UIWindow(windowScene: windowScene)
window.rootViewController = UIHostingController(rootView: ContentView())
self.window = window
window.makeKeyAndVisible()
}
取自
我有一个使用 Main.storyboard 在 Xcode 10 中制作的应用程序,我想将其迁移以使用 Apple 的新框架:SwiftUI。
已经可以了吗?
我已经尝试在 Info.plist
中添加 UIApplicationSceneManifest
键,我将 AppDelegate.swift
更改为使用场景,我创建了 SceneDelegate.swift
即使这样我也可以不是
我假设您使用的是 Xcode 11 GM
和 macOS Mojave
或 Catalina
。
随着 plist
中的更改,您必须在应用程序委托中添加 UISceneSession
生命周期函数。
func application(_ application: UIApplication,
configurationForConnecting connectingSceneSession: UISceneSession,
options: UIScene.ConnectionOptions) -> UISceneConfiguration {
// The name must match the one in the Info.plist
return UISceneConfiguration(name: "Default Configuration", sessionRole: connectingSceneSession.role)
}
func application(_ application: UIApplication, didDiscardSceneSessions sceneSessions: Set<UISceneSession>) {
}
此外,您需要确保 window
在 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 = UIHostingController(rootView: ContentView())
self.window = window
window.makeKeyAndVisible()
}
其中 ContentView
是您要显示的主要 SwiftUI
视图。
P.S。确保 plist
指定 $(PRODUCT_MODULE_NAME).SceneDelegate
作为委托 class 名称,场景委托称为 SceneDelegate
示例:
如果您使用 Catalina
,您可以在目标的构建设置中打开 Previews
。
构建选项 -> 启用预览
附录 I:
确保从 Info.Plist 和 you're targeting iOS 13
.
附录二:
清洁 Derived Data
,正如评论中的许多开发者所建议的那样。
我的解决方案原来是不同的。在我的例子中,我已经准备好了一切,但是当代码试图加载 UISceneConfiguration
时,它无法加载 Info.plist
中的配置,而是给了我一个辅助 window 配置没有设置场景委托。如果我从调试控制台请求正确的配置,它将按预期加载。我一头雾水。
我仔细检查了所有内容并尝试了此处的所有建议,但 none 奏效了。最后我在模拟器上做了 'Hardware' - 'Erase all contents and settings...' 并解决了它。
我的猜测是,因为我在模拟器上使用的是 运行 应用程序的 pre-SwiftUI 版本,所以其中的某些内容导致 SwiftUI 版本的行为有所不同。
这是一个正确的小改动
在SceneDelegate.swift
中替换
let window = UIWindow(frame: UIScreen.main.bounds)
window.rootViewController = UIHostingController(rootView: ContentView())
self.window = window
window.makeKeyAndVisible()
和
if let windowScene = scene as? UIWindowScene {
let window = UIWindow(windowScene: windowScene)
window.rootViewController = UIHostingController(rootView: ContentView())
self.window = window
window.makeKeyAndVisible()
}
取自