swift - 如何在 Swift 4 中压缩文件时显示进度 HUD?

标签 swift zip progress-bar swift4 hud

我正在使用 marmelroy/Zip framework在我的项目中压缩/解压缩文件,和JGProgressHUD显示操作的进度。

如果我尝试从 ViewDidLoad 方法中显示它,我可以看到 HUD,但是如果我在与 quickZipFiles 方法的进度功能关联的闭包中使用它(如代码示例),则 HUD 是在操作结束时显示。

我想这可能与计时问题有关,但由于我不太喜欢完成处理程序、闭包和 GDC(线程、异步任务等),所以我想征求一下建议。

有什么想法吗?

// In my class properties declaration
var hud = JGProgressHUD(style: .dark)

// In my ViewDidLoad
self.hud.indicatorView = JGProgressHUDPieIndicatorView()
self.hud.backgroundColor = UIColor(white: 0, alpha: 0.7)

// In my method
do {
    self.hud.textLabel.text = NSLocalizedString("Zipping files...", comment: "Zipping File Message")
    self.hud.detailTextLabel.text = "0%"
    if !(self.hud.isVisible) {
        self.hud.show(in: self.view)
    }
    zipURL = try Zip.quickZipFiles(documentsList, fileName: "documents", progress: { (progress) -> () in
        let progressMessage = "\(round(progress*100))%"
        print(progressMessage)
        self.hud.setProgress(Float(progress), animated: true)
        self.hud.textLabel.text = NSLocalizedString("Zipping files...", comment: "Zipping File Message")
        self.hud.detailTextLabel.text = progressMessage
        if (progress == 1.0) {
            self.hud.dismiss()
        }
    })
} catch {
    print("Error while creating zip...")
}

最佳答案

ZIP Foundation内置了对进度报告和取消的支持。
因此,如果您可以切换 ZIP 库,这可能更适合您的项目。 (完全披露:我是这个图书馆的作者)

下面是一些示例代码,展示了如何压缩目录并在 JGProgressHUD 上显示操作进度。我只是在这里压缩主包的目录作为示例。

ZIP 操作在单独的线程上分派(dispatch),以便您的主线程可以更新 UI。 progress var 是默认的 Foundation (NS)Progress通过 KVO 报告变化的对象。

import UIKit
import ZIPFoundation
import JGProgressHUD

class ViewController: UIViewController {

    @IBOutlet weak var progressLabel: UILabel!
    var indicator = JGProgressHUD()
    var isObservingProgress = false
    var progressViewKVOContext = 0

    @objc
    var progress: Progress?

    func startObservingProgress()
    {
        guard !isObservingProgress else { return }

        progress = Progress()
        progress?.completedUnitCount = 0
        self.indicator.progress = 0.0

        self.addObserver(self, forKeyPath: #keyPath(progress.fractionCompleted), options: [.new], context: &progressViewKVOContext)
        isObservingProgress = true
    }

    func stopObservingProgress()
    {
        guard isObservingProgress else { return }

        self.removeObserver(self, forKeyPath: #keyPath(progress.fractionCompleted))
        isObservingProgress = false
        self.progress = nil
    }

    override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
        if keyPath == #keyPath(progress.fractionCompleted) {
            DispatchQueue.main.async {
                self.indicator.progress = Float(self.progress?.fractionCompleted ?? 0.0)
                if let progressDescription = self.progress?.localizedDescription {
                    self.progressLabel.text = progressDescription
                }

                if self.progress?.isFinished == true {
                    self.progressLabel.text = ""
                    self.indicator.progress = 0.0
                }
            }
        } else {
            super.observeValue(forKeyPath: keyPath, of: object, change: change, context: context)
        }
    }

    @IBAction func cancel(_ sender: Any) {
        self.progress?.cancel()
    }

    @IBAction func createFullArchive(_ sender: Any) {
        let directoryURL = Bundle.main.bundleURL

        let tempArchiveURL = URL(fileURLWithPath: NSTemporaryDirectory()).appendingPathComponent(ProcessInfo.processInfo.globallyUniqueString).appendingPathExtension("zip")
        self.startObservingProgress()
        DispatchQueue.global().async {
            try? FileManager.default.zipItem(at: directoryURL, to: tempArchiveURL, progress: self.progress)
            self.stopObservingProgress()
        }
    }
}

关于swift - 如何在 Swift 4 中压缩文件时显示进度 HUD?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48972943/

相关文章:

ios - UIImage 返回 nil 但存在

ios iAd 在显示前加载

ios - UITests Xcode7 : How to adjust date picker with multiply pickers?

具有按比例填充的 subview 和固有宽度的 iOS StackView 的行为不符合预期

ios - 从存档中解压缩单个文件

android - ProgressBar/ProgressDialog 的自定义 Drawable

list - 如何在 Scala 中制作简单的列表?

PHP ZipArchive::open 总是导致 ZIPARCHIVE::ER_READ 错误

c# - 如何在加载某些控件时显示进度条?

Android Drawable mutate() 和 setLevel()