如何在 Swift Xcode iOS 中以编程方式延迟启动画面
How can I delay splash launch screen programmatically in Swift Xcode iOS
我在LaunchStoreyboard
中的imageView
中放了一个image
。如何以编程方式延迟图像时间?
这里是Launch Screen Guideline from Apple.
这是启动屏幕视图控制器的代码:
import UIKit
class LaunshViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
self.delay(0.4)
}
func delay(_ delay:Double, closure:@escaping ()->()) {
let when = DispatchTime.now() + delay
DispatchQueue.main.asyncAfter(deadline: when, execute: closure)
}
}
在AppDelegate中放一行代码class -
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
Thread.sleep(forTimeInterval: 3.0)
// Override point for customization after application launch.
return true
}
创建一个ViewController并使用NSTimer检测延迟时间。当计时器结束时推送第一个 UIViewcontroller。
在 ViewDidLoad 方法中..
[NSTimer scheduledTimerWithTimeInterval:2.0 target:self selector:@selector(fireMethod) userInfo:nil repeats:NO];
-(void)fireMethod
{
// push view controller here..
}
不建议将整个应用程序设置为等待状态。
如果应用程序需要在完成看门狗之前做更多工作,则可能会因启动时间过长而终止应用程序。
相反,您可以执行类似这样的操作来延迟启动屏幕。
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
window = UIWindow(frame: UIScreen.main.bounds)
window?.rootViewController = UIStoryboard(name: "LaunchScreen", bundle: nil).instantiateInitialViewController()
window?.makeKeyAndVisible()
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 3) {
self.window?.rootViewController = UIStoryboard(name: "Main", bundle: nil).instantiateInitialViewController()
}
return true
}
Swift 4.x
让您的应用程序休眠不是一个好习惯!
启动您的应用程序应该尽可能快,因此您不希望使用启动屏幕延迟。
但是,您可以 运行 一个 loop
而不是 睡眠 ,在此期间接收器处理来自所有附加输入源的数据:
这将延长启动屏幕的可见时间。
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
RunLoop.current.run(until: NSDate(timeIntervalSinceNow:1) as Date)
return true
}
您的应用绝对 不应 进入睡眠状态,因为它可能会因长时间无响应而被 OS 杀死。
如果您在启动屏幕上使用静态图像,对我有用的是使用 LaunchScreen.storyboard 中的图像,然后当您的主屏幕控制器启动,在主控制器的 ViewDidAppear 中以模态方式呈现与背景相同的图像 VC(动画设置为 false)。
然后您可以使用您的逻辑来了解何时关闭启动屏幕(VC 中的 dismiss 方法,动画设置为 false)。
从 actual LaunchScreen 到我的 VC 呈现相同屏幕的过渡在我看来是难以察觉的。
PS:ViewDidAppear方法可能会被多次调用,在这种情况下,您需要使用逻辑来不会第二次在启动屏幕上显示 VC。
Swift 5.x, iOS 13.x.x
在AppDelegate class中修改以下函数在Swift中不起作用 5.x/iOS 13.x.x.
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
return true
}
相反,您必须修改 SceneDelegate 中的 scene 函数 class 如下。 LaunchSceen 会延迟 3 秒。
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
window?.rootViewController = UIStoryboard(name: "LaunchScreen", bundle: nil).instantiateInitialViewController()
window?.makeKeyAndVisible()
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 3) {
self.window?.rootViewController = UIStoryboard(name: "Main", bundle: nil).instantiateInitialViewController()
}
guard let _ = (scene as? UIWindowScene) else { return }
}
window 变量应该已经存在于 SceneDelegate class 中,如下所示。
var window: UIWindow?
SwiftUI
对于 SwiftUI,您可以将与接受的答案非常相似的代码放入 ContentView.onAppearing:
struct ContentView: View {
var body: some View {
Text("Hello")
.onAppear {
Thread.sleep(forTimeInterval: 3.0)
}
}
}
让线程休眠不是一个好主意。
我建议您转到 SceneDelegate 的“willConnectTo”函数并粘贴这段代码,您就可以开始了。
window?.rootViewController = UIStoryboard(name: "LaunchScreen", bundle: nil).instantiateInitialViewController()
window?.makeKeyAndVisible()
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 3) {
self.window?.rootViewController = UIStoryboard(name: "Main", bundle: nil).instantiateInitialViewController()
}
guard let _ = (scene as? UIWindowScene) else { return }
我在LaunchStoreyboard
中的imageView
中放了一个image
。如何以编程方式延迟图像时间?
这里是Launch Screen Guideline from Apple.
这是启动屏幕视图控制器的代码:
import UIKit
class LaunshViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
self.delay(0.4)
}
func delay(_ delay:Double, closure:@escaping ()->()) {
let when = DispatchTime.now() + delay
DispatchQueue.main.asyncAfter(deadline: when, execute: closure)
}
}
在AppDelegate中放一行代码class -
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
Thread.sleep(forTimeInterval: 3.0)
// Override point for customization after application launch.
return true
}
创建一个ViewController并使用NSTimer检测延迟时间。当计时器结束时推送第一个 UIViewcontroller。
在 ViewDidLoad 方法中..
[NSTimer scheduledTimerWithTimeInterval:2.0 target:self selector:@selector(fireMethod) userInfo:nil repeats:NO];
-(void)fireMethod
{
// push view controller here..
}
不建议将整个应用程序设置为等待状态。 如果应用程序需要在完成看门狗之前做更多工作,则可能会因启动时间过长而终止应用程序。
相反,您可以执行类似这样的操作来延迟启动屏幕。
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
window = UIWindow(frame: UIScreen.main.bounds)
window?.rootViewController = UIStoryboard(name: "LaunchScreen", bundle: nil).instantiateInitialViewController()
window?.makeKeyAndVisible()
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 3) {
self.window?.rootViewController = UIStoryboard(name: "Main", bundle: nil).instantiateInitialViewController()
}
return true
}
Swift 4.x
让您的应用程序休眠不是一个好习惯!
启动您的应用程序应该尽可能快,因此您不希望使用启动屏幕延迟。
但是,您可以 运行 一个 loop
而不是 睡眠 ,在此期间接收器处理来自所有附加输入源的数据:
这将延长启动屏幕的可见时间。
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
RunLoop.current.run(until: NSDate(timeIntervalSinceNow:1) as Date)
return true
}
您的应用绝对 不应 进入睡眠状态,因为它可能会因长时间无响应而被 OS 杀死。
如果您在启动屏幕上使用静态图像,对我有用的是使用 LaunchScreen.storyboard 中的图像,然后当您的主屏幕控制器启动,在主控制器的 ViewDidAppear 中以模态方式呈现与背景相同的图像 VC(动画设置为 false)。
然后您可以使用您的逻辑来了解何时关闭启动屏幕(VC 中的 dismiss 方法,动画设置为 false)。
从 actual LaunchScreen 到我的 VC 呈现相同屏幕的过渡在我看来是难以察觉的。
PS:ViewDidAppear方法可能会被多次调用,在这种情况下,您需要使用逻辑来不会第二次在启动屏幕上显示 VC。
Swift 5.x, iOS 13.x.x
在AppDelegate class中修改以下函数在Swift中不起作用 5.x/iOS 13.x.x.
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
return true
}
相反,您必须修改 SceneDelegate 中的 scene 函数 class 如下。 LaunchSceen 会延迟 3 秒。
func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
window?.rootViewController = UIStoryboard(name: "LaunchScreen", bundle: nil).instantiateInitialViewController()
window?.makeKeyAndVisible()
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 3) {
self.window?.rootViewController = UIStoryboard(name: "Main", bundle: nil).instantiateInitialViewController()
}
guard let _ = (scene as? UIWindowScene) else { return }
}
window 变量应该已经存在于 SceneDelegate class 中,如下所示。
var window: UIWindow?
SwiftUI
对于 SwiftUI,您可以将与接受的答案非常相似的代码放入 ContentView.onAppearing:
struct ContentView: View {
var body: some View {
Text("Hello")
.onAppear {
Thread.sleep(forTimeInterval: 3.0)
}
}
}
让线程休眠不是一个好主意。
我建议您转到 SceneDelegate 的“willConnectTo”函数并粘贴这段代码,您就可以开始了。
window?.rootViewController = UIStoryboard(name: "LaunchScreen", bundle: nil).instantiateInitialViewController()
window?.makeKeyAndVisible()
DispatchQueue.main.asyncAfter(deadline: DispatchTime.now() + 3) {
self.window?.rootViewController = UIStoryboard(name: "Main", bundle: nil).instantiateInitialViewController()
}
guard let _ = (scene as? UIWindowScene) else { return }