因此,在我的应用中,每当用户返回应用时,我都会有一个我想要更新的Feed。
我正在applicationWillEnterForeground
AppDelegate
@UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
let mainViewController = MainViewController()
func applicationWillEnterForeground(_ application: UIApplication) {
mainViewController.refreshLatestVideos()
}
}
class MainViewController: UITabBarController {
private var subscriptionsController: SubscriptionsController! // initialized on viewDidLoad
func refreshLatestVideos() {
subscriptionsController.refreshLatestVideos(sender: nil)
}
}
class SubscriptionsController: UITableViewController {
private var subscriptionsModelController: SubscriptionsModelController! // received on constructor
@objc func refreshLatestVideos(sender:UIButton!) {
showMessage(message: "Updating subscriptions...") // this message is always shown to me
subscriptionsModelController.loadLatestVideos()
}
}
class SubscriptionsModelController {
func loadLatestVideos() {
UIApplication.shared.isNetworkActivityIndicatorVisible = true
DispatchQueue.global(qos: .userInitiated).async {
// bunch of requests with Just
...
// update message
showMessage(message: "Updating subscription x of y") // this message sometimes doesn't appear, because the UI is frozen
// another requests
...
// update message
showMessage(message: "Updates completed")
}
}
}
调用例程来执行此操作。
一切正常,但有时,我的UI在此操作期间冻结。
我能够使用标签找到这种情况的进展,以显示此例程的进度。标签更新了三个主要观点:
有时,此工作流程运行正常,我可以通过此标签查看进度。 但有时,标签只显示第一条消息,并且不会出现在例程中发生的消息。除此之外,我无法在我的应用上做任何事情,因为用户界面被冻结了。一旦例程结束,一切都恢复正常。
这是我的应用程序为调用此例程而执行的流程的简化版本:
<baseAddresses><add baseAddress="localhost:1234/GettingStartedLib/CalculatorService.vsc"/>
</baseAddresses>
如您所见,我在全局队列中执行更新,因此我没有阻止主线程。 而且,UI的冻结有时只会发生。
有什么意义我可以看一下发现了什么?主线程是否可能被其他东西阻止?
答案 0 :(得分:3)
将UI更新到主线程:
DispatchQueue.main.async { showMessage(message: "Updates completed") }
每当你以任何方式访问/修改用户界面时,都会在主线程上进行操作以避免出现意外问题(link到这个主题的多个资源之一,我建议你google up并阅读更多)。
这也适用于其余的代码,如果有与UI相关的内容,也可以为它做同样的事情 - 例如,如果在完成任务后调用tableView.reloadData
,则在主要代码上执行线程也是如此。