我需要解析相当多的文本,并希望在发生这种情况时向用户提供一些反馈。
环境是Swift,虽然我确实在Obj-C中看到了一些代码([self performSelector:@selector(.....)),但它并没有多大意义。如果我知道如何接受并将其嵌入到Swift方法中,我会这样做。
我可以通过一个可重复的小案例来总结问题,从而得到相同的结果。即在循环内,增加一个值,显示进度并返回完成。显然,进度不会显示,因为iOS会在刷新屏幕之前等待循环完成。
这确实有意义,所以我希望在继续处理之前以不同的间隔中断处理(即循环)并刷新进度条。
我目前的代码如下:
@IBAction func goButton(sender: UIButton) {
currentCounter = 0
target = textTarget.text.toInt()!
step = textStep.text.toInt()!
updateProgressBar()
while currentCounter < target {
currentCounter += step
updateProgressBar()
}
}
func updateProgressBar() {
var percentage = Float(currentCounter) / Float(target) * 100
progressPercentage.text = "\(percentage) %"
println("progress = \(percentage)")
progressBar.setProgress(percentage, animated: false)
}
我见过以下内容:
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)) {
// do some task here...
}
dispatch_async(dispatch_get_main_queue()) {
// do another task here...
}
我如何使用这种方法(如果它是相关的),如果我这样做,处理与刷新调用的位置会在哪里?
乔恩
答案 0 :(得分:4)
GCD( Grand Central Dispatch )绝对是更好的选择。它使用简单,功能强大且直观,尽管语法最初可能会另有说明。
在进行耗时的工作时更新UI的方法的要点始终如下:
dispatch_async
与主队列以外的队列一起使用(可以使用内置队列进行此操作,也可以创建自己的队列)dispatch_async
内,您可以更新用户界面。有关在Swift环境中使用GCD的精彩而全面的教程,请查看this。
答案 1 :(得分:3)
以下是对代码的更新答案,因为我认为其他人将从模式中受益:
@IBAction func goButton(sender: UIButton) {
target = textTarget.text.toInt()!
step = textStep.text.toInt()!
currentCounter = 0
updateProgressBar()
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)) {
self.doTimeConsumingWork()
}
}
func doTimeConsumingWork() {
while currentCounter < target {
currentCounter += step
percentage = Float(currentCounter) / Float(target) * 100
if (percentage > 0.0) && (percentage % 10.0) == 0.0 {
// This is the important bit :)
// I chose to do this synchronously (not async) since progress updating can actually be done quite a while after the time consuming work is over
dispatch_sync(dispatch_get_main_queue()) {
self.updateProgressBar()
}
}
}
println("Finished doing time consuming work")
}
func updateProgressBar() {
progressPercentage.text = "\(percentage) %"
println("target = \(target), step = \(step) progress = \(percentage)")
progressBar.setProgress(percentage / 100.0, animated: false)
}