如何挂起主队列上的工作项



我想知道是否可以在保持".asyncAfter"时间的同时挂起然后恢复主队列上的工作项。如果没有,是否有解决方法来实现这一点?

在某个时刻,我将以下DispatchWorkItem排队:

dispatchWorkItem = DispatchWorkItem(qos: .userInteractive, block: {
self.view.backgroundColor = UIColor.workoutBackgroundColor
self.runTimer()
self.timerButton.animateableTrackLayer.removeAnimation(forKey: "strokeEndAnimation")
self.isRestState = false
})

我使用排队

DispatchQueue.main.asyncAfter(deadline: delayTime, execute: self.dispatchWorkItem))

(delayTime是函数的参数(

现在,我遇到的问题是,如果用户在我的应用程序中执行"暂停"操作,我如何暂停此工作项。

我已经尝试使用DispatchQueue.main.suspend()方法,但工作项在指定的延迟时间后继续执行。根据我所读到的内容,这个方法应该挂起队列和这个排队的工作项,因为它没有被执行。(如果我错了,请纠正我!(

我需要实现的是工作项目被"暂停",直到用户在应用程序中执行"恢复"操作,该操作将从延迟时间结束的地方恢复工作项目。

这适用于我在不需要进行UI更新时创建的后台队列;然而,在主队列上的is似乎步履蹒跚。

我考虑过的一种解决方法是,当用户执行暂停操作时,存储工作项将被执行之前的剩余时间,并在继续操作时将该时间重新添加到队列中。这似乎是一种质量很差的方法,我觉得有一种更合适的方法。

在此基础上,是否可以创建一个后台队列,在执行时执行主队列上的工作项?

提前感谢!

在这方面,是否可以创建一个后台队列,在执行时在主队列上执行工作项?

你的建议是这样的:

var q = DispatchQueue(label: "myqueue")
func configAndStart(seconds:TimeInterval, handler:@escaping ()->Void) {
self.q.asyncAfter(deadline: .now() + seconds, execute: {
DispatchQueue.main.async(execute: handler())
})
}
func pause() {
self.q.suspend()
}
func resume() {
self.q.resume()
}

但我的实际测试似乎表明,这不会如你所愿;倒计时不会从暂停的地方恢复。

我考虑过的一种解决方法是,当用户执行暂停操作时,存储执行工作项之前的剩余时间,并在恢复操作时将该时间重新添加到队列中。这似乎是一种质量很差的方法,我觉得有一种更合适的方法。

质量并不差。没有用于暂停调度计时器倒计时或内省计时器的内置机制,因此,如果您想在主队列上完成整件事,您唯一的办法就是按照您所说的:维护您自己的计时器和必要的状态变量。这是一个我蹒跚而行的相当愚蠢的模型:

class PausableTimer {
var t : DispatchSourceTimer!
var d : Date!
var orig : TimeInterval = 0
var diff : TimeInterval = 0
var f : (()->Void)!
func configAndStart(seconds:TimeInterval, handler:@escaping ()->Void) {
orig = seconds
f = handler
t = DispatchSource.makeTimerSource()
t.schedule(deadline: DispatchTime.now()+orig, repeating: .never)
t.setEventHandler(handler: f)
d = Date()
t.resume()
}
func pause() {
t.cancel()
diff = Date().timeIntervalSince(d)
}
func resume() {
orig = orig-diff
t = DispatchSource.makeTimerSource()
t.schedule(deadline: DispatchTime.now()+orig, repeating: .never)
t.setEventHandler(handler: f)
t.resume()
}
}

这在我粗糙的测试中起到了作用,似乎可以根据需要中断(贫困(,但不要引用我的话;我没有花太多时间在上面。细节留给读者练习!

相关内容

  • 没有找到相关文章

最新更新