Xcode UIView.init(frame:) must be used from main thread only
我试图在后台线程中呈现一些视图,以不影响主线程。 在Xcode 9之前,这从来都不是问题。
1 2 3 4 5 6 | DispatchQueue.global(qos: .background).async { let customView = UIView(frame: .zero) DispatchQueue.main.async { self.view.addSubview(customView) } } |
UIView.init(frame:) must be used from main thread only
在第二行中发生此错误。
更新资料
Apple
Manipulations to your application’s user interface must occur on the main thread. Thus, you should always call the methods of the UIView class from code running in the main thread of your application. The only time this may not be strictly necessary is when creating the view object itself, but all other manipulations should occur on the main thread.
Xcode 9有一个新的运行时主线程检查器,它可以检测从后台线程对UIKit的调用并生成警告。
我知道它的意思是生成警告而不会使应用程序崩溃,但是您可以尝试为测试目标禁用主线程检查器。
我在一个示例项目中尝试了此代码,调试器在该问题上暂停了(如预期的那样),但该应用程序并未崩溃。
1 2 3 4 5 6 7 | override func viewDidLoad() { super.viewDidLoad() DispatchQueue.global().async { let v = UIView(frame: .zero) } } |
您可以使用此功能
1 2 3 4 5 6 7 8 9 10 | func downloadImage(urlstr: String, imageView: UIImageView) { let url = URL(string: urlstr)! let task = URLSession.shared.dataTask(with: url) { data, _, _ in guard let data = data else { return } DispatchQueue.main.async { // Make sure you're on the main thread here imageview.image = UIImage(data: data) } } task.resume() } |
如何使用此功能?
1 | downloadImage(urlstr:"imageUrl", imageView: self.myImageView) |
主线程入口
您可以按如下方式输入主线程
1 2 3 | DispatchQueue.main.async { // UIView usage } |