iOS 全网最准确的倒计时方法
2021-11-18 本文已影响0人
KingWorld
背景:因为app上用到很多倒计时,但是当app挂在后台或者有其它情况,就很容易导致倒计时计时不准确,为此有一个提高倒计时的准确性方法
方法概念
1.后端返回后端服务器时间与准备开始时间,计算出两者时间差
2.用手机当前时间与时间差每秒相减,就是倒计时的值
//活动 3: 进行中 2:未开始 1:已结束
var sort = 1
//结束时间
var date_end = ""
//开始时间
var date_start = ""
//系统当前时间
var current_time = ""
//倒计时日历
var com:DateComponents?
//倒计时相差秒数
var instanceT: Int64?
var instanceTime : Int64?{
get{
if let t = instanceT{
return t
}
let format = DateFormatter()
format.dateFormat = "yyyy-MM-dd HH:mm:ss"
var endT : Date
if sort == 2 {
endT = format.date(from: date_start) ?? Date()
} else if sort == 3 {
endT = format.date(from: date_end) ?? Date()
} else {
endT = Date()
}
let endSeconds = endT.timeIntervalSince1970
let currentT = format.date(from: current_time)
let currentSeconds = currentT?.timeIntervalSince1970
//计算相差秒数
if let current = currentSeconds,endSeconds > current {
instanceT = Int64(endSeconds - current)
return Int64(endSeconds - current)
}
return nil
}
set{
instanceT = newValue
}
}
在cell上
var timer : DispatchSourceTimer?
func setUpTimer(vm:ViewModel) {
if let _ = timer{
return;
}
if let insatnceT = vm.instanceTime,insatnceT > 0{
//将相差秒数与当前手机时间相加,到时候用这时间每秒减去当前时间用来倒数
entTime = Date().timeIntervalSince1970 + Double(insatnceT)
handTime(insatnceT)
timer = DispatchSource.makeTimerSource(flags: [], queue: DispatchQueue.global())
// let timer = DispatchSource.makeTimerSource()
/*
dealine: 开始执行时间
repeating: 重复时间间隔
leeway: 时间精度
*/
timer?.schedule(deadline: .now(), repeating: DispatchTimeInterval.seconds(1), leeway: DispatchTimeInterval.seconds(0))
// timer 添加事件
timer?.setEventHandler {[weak self] in
//每秒减去当前时间用来倒数
if let endT = self?.entTime,endT - Date().timeIntervalSince1970 > 0{
let insatnceT = endT - Date().timeIntervalSince1970
DispatchQueue.main.async {
self?.handTime(Int64(insatnceT))
}
}else{
DispatchQueue.main.async {
//处理UI界面
self?.timeLabList[1].text = "00"
self?.timeLabList[2].text = "00"
self?.timeLabList[3].text = "00"
}
//倒数结束后将timer释放
self?.removeData()
//时间倒数结束之后回调
self?.didTimeOver?()
}
}
timer?.resume()
}
}
func removeData(){
guard let t = timer else {
return
}
t.cancel()
timer = nil
}
//根据秒数计算出天,时,分,秒
func handTime(_ seconds:Int64){
var remainS = seconds
let days = remainS/(24 * 60 * 60)
remainS = remainS%(24 * 60 * 60)
let h = remainS/(60 * 60)
remainS = remainS%(60 * 60)
let m = remainS/60
let s = remainS%60
}