UIImage(data:Data)是否异步?

问题描述 投票:0回答:1

[我的问题:我有理由相信,从UIImage初始化Data会使我的主线程有点麻烦。它并不可怕,只需花费一秒钟的时间即可完成,但是它很引人注目,因为它使我的UI看起来有点毛病。

我在做什么:我有一个UIPageViewController。所述UIViewController表示的UIPageViewController之一正在其UIImage(data: Data)方法中使用此viewDidLoad初始化程序:

class PageViewController: UIPageViewController {

    var pages: [UIViewController] = []

    override func viewDidLoad() {
        super.viewDidLoad()
        loadPages()
    }

    ...

    func loadPages() {

        let vc1 = storyboard!.instantiateViewController(withIdentifier: "VC1") as! ViewController1
        let vc2 = storyboard!.instantiateViewController(withIdentifier: "VC2") as! ViewController2
        let vc3 = storyboard!.instantiateViewController(withIdentifier: "VC3") as! ViewController3
        pages.append(userProfilePreviewVC)
        pages.append(meetVC)
        pages.append(chatLogVC)

        setViewControllers([pages[1]], direction: UIPageViewController.NavigationDirection.forward, animated: false, completion: nil)
    }
}

extension PageViewController: UIPageViewControllerDelegate, UIPageViewControllerDataSource {
    func pageViewController(_ pageViewController: UIPageViewController, viewControllerBefore viewController: UIViewController) -> UIViewController? {

        switch currentIndex {
        case 1:
            return pages[0]
        case 2:
            return pages[1]
        default:
            return nil
        }
    }

    func pageViewController(_ pageViewController: UIPageViewController, viewControllerAfter viewController: UIViewController) -> UIViewController? {
        switch currentIndex {
        case 0:
            return pages[1]
        case 1:
            return pages[2]
        default:
            return nil
        }
    }
}

这里是问题所在:

class ViewController1: UIViewController {

    @IBOutlet var profilePicButton: UIButton!

    override func viewDidLoad() {
        super.viewDidLoad()
        let userPhotos = UserDefaults.standard.array(forKey: "UserPhotos") as? [Data] ?? []
        if userPhotos.count != 0 {
            self.profilePicButton.setImage(UIImage(data: userPhotos.first ?? Data()) ?? UIImage(named: "profile")!, for: .normal)
        } else {
            self.profilePicButton.setImage(UIImage(named: "profile"), for: .normal)
        }
    }
}

我的问题:PageViewController上滑动到显示ViewController1的页面时,主线程似乎阻塞了,因为实际加载此ViewController1需要花费一秒钟的时间。与之相反的是,其他视图控制器在滑向它们时立即准备就绪。同样,当用户没有任何存储的个人资料图片数据时,将使用我的assets.xcassets文件夹中的占位符图像代替它。呈现此图像时没有滞后。我的问题是:我应该在后台线程上使用UIImage(data: Data)并在UIImage初始化后更新按钮图像吗?

swift asynchronous uiimage uikit nsdata
1个回答
0
投票

我已经能够通过在后台线程上初始化UIImage并当然在主线程上更新profilePicButton的图像来解决我的问题:

class ViewController1: UIViewController {

    @IBOutlet var profilePicButton: UIButton!

    override func viewDidLoad() {
        super.viewDidLoad()
        let userPhotos = UserDefaults.standard.array(forKey: "UserPhotos") as? [Data] ?? []
        if userPhotos.count != 0 {
            DispatchQueue.global(qos: .background).async {
                let image = UIImage(data: userPhotos.first ?? Data()) ?? UIImage(named: "profile")!

                DispatchQueue.main.async {
                    self.profilePicButton.setImage(image, for: .normal)
                }
            }
        } else {
            self.profilePicButton.setImage(UIImage(named: "profile"), for: .normal)
        }
    }
}

[这使我相信,是的,从主线程上的UIImage初始化Data是一个坏主意。您可能希望在后台线程上初始化图像并更新该线程。主线程上的UI。

[如果有人知道为什么UIImage(data: Data)会堵塞主线程,请让我知道,因为我仍然对为什么会这样感到好奇。

© www.soinside.com 2019 - 2024. All rights reserved.