Search code examples
iosswiftcountdown

Countdown in seconds only (form 00:20 to 0) using NSTimer


I need to have a label countdown from 20secs to 0 and start over again. This is my first time doing a project in Swift and I am trying to use NSTimer.scheduledTimerWithTimeInterval. This countdown should run in a loop for a given amount of times.

I am having a hard time implementing a Start and Start again method (loop). I basically am not finding a way to start the clock for 20s and when it's over, start it again.

I'd appreciate any idea on how to do that Wagner

 @IBAction func startWorkout(sender: AnyObject) {

    timer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: Selector("countDownTime"), userInfo: nil, repeats: true)
    startTime = NSDate.timeIntervalSinceReferenceDate()

}

func countDownTime() {

    var currentTime = NSDate.timeIntervalSinceReferenceDate()

    //Find the difference between current time and start time.
    var elapsedTime: NSTimeInterval = currentTime - startTime

    //calculate the seconds in elapsed time.
    let seconds = UInt8(elapsedTime)
    elapsedTime -= NSTimeInterval(seconds)

    //find out the fraction of milliseconds to be displayed.
    let fraction = UInt8(elapsedTime * 100)

    //add the leading zero for minutes, seconds and millseconds and store them as string constants
    let strSeconds = seconds > 9 ? String(seconds):"0" + String(seconds)
    let strFraction = fraction > 9 ? String(fraction):"0" + String(fraction)

    //concatenate minuets, seconds and milliseconds as assign it to the UILabel
    timeLabel.text = "\(strSeconds):\(strFraction)"
}

Solution

  • You should set your date endTime 20s from now and just check the date timeIntervalSinceNow. Once the timeInterval reaches 0 you set it 20 seconds from now again

    import UIKit
    
    class ViewController: UIViewController {
    
        @IBOutlet weak var strTimer: UILabel!
    
        var endTime = Date(timeIntervalSinceNow: 20)
        var timer = Timer()
    
        @objc func updateTimer(_ timer: Timer) {
            let remaining = endTime.timeIntervalSinceNow
            strTimer.text = remaining.time
            if remaining <= 0 {
                endTime += 20
            }
        }
    
        override func viewDidLoad() {
            super.viewDidLoad()
            strTimer.font = .monospacedSystemFont(ofSize: 20, weight: .semibold)
            strTimer.text =  "20:00"
            timer = .scheduledTimer(timeInterval: 1/30, target: self, selector: #selector(updateTimer), userInfo: nil, repeats: true)
        }
    
    }
    

    extension TimeInterval {
        var time: String {
            String(format: "%02d:%02d", Int(truncatingRemainder(dividingBy: 60)), Int((self * 100).truncatingRemainder(dividingBy: 100)))
        }
    }