There comes a time in your swift development that you will find the need to schedule when to fire your code, or you might want to give your user some time to think about what they want to do like a countdown timer. In this article we will discuss about timers and how to use them.
Timer is Swift is part of the Foundations framework so in order to use it in on your app you must import Foundations first.
import Foundation
You are now ready to to timers in your app!
The Basics – Scheduled Timer
The basic use for a timer is called the scheduledTimer where you need to set the timeInterval, selector, and repeats. The timeInterval is set to how many seconds elapsed to call the function/selector. The selector serves as the function/action that the timer calls when it fires. Finally, repeats is a boolean variable that indicates if the timer should be repeating or it fires only once.
A Basic timer is declared as such:
//declare blank timer variable var timer = Timer() //in a function or viewDidLoad() timer = Timer.scheduledTimer(timeInterval: 1.0, target: self, selector: #selector(timerAction), userInfo: nil, repeats: true) //new function @objc func timerAction(){ print(“timer fired!”) }
Notice that the function has an @objc. This is because it is needed to create a selector which is a requirement for our timer.
In order for the timer to only fire once the option repeats should be set to false
timer = Timer.scheduledTimer(timeInterval: 1.0, target: self, selector: #selector(timerAction), userInfo: nil, repeats: false)
In the instance that you have a repeating timer you can manually stop your timer according to your preference by calling .invalidate, you can do this on your selector.
//in a function or viewDidLoad() timer = Timer.scheduledTimer(timeInterval: 1.0, target: self, selector: #selector(timerAction), userInfo: nil, repeats: true) //new function @objc func timerAction(){ print(“timer fired!”) timer.invalidate() }
Scheduled Timer with Defined Selector
A timer can also have an already defined selector, which means no need to create a separate function for it. In order to do so just do this:
Timer.scheduledTimer(withTimeInterval: 1.0, repeats: true) { timer in print("timer fired!") timer.invalidate() }
Having this option also lets us easily create and manage what we want our timer to do, lets say we create a countdown timer we can simply define our timer like this:
var timeLeft = 10 Timer.scheduledTimer(withTimeInterval: 1.0, repeats: true) { timer in print("timer fired!") timeLeft -= 1 self.timerTextField.text = String(timeLeft) print(timeLeft) if(timeLeft==0){ timer.invalidate() } }
Notice how we can use variables in our selector, just be sure to declare a variable first if you plan on using one.
Timer tolerance
Timer tolerance is set when you can tolerate your timer fire to be a bit late. Why would you want your timer to be a bit late, you ask? Simply, it’s because it can contribute to power consumption. Remember that your app, specially when there is a timer running in the background, will have a hard time managing your state. By setting a tolerance we are letting the app have more time to properly execute different kinds of code and this in turn lowers battery consumption of your app.
In order to set tolerance just define as:
timer = Timer.scheduledTimer(timeInterval: 1.0, target: self, selector: #selector(timerAction), userInfo: nil, repeats: true) timer.tolerance = 0.3
Note: it is important to note that tolerance can make your app late, but it will never execute your code early.
Timer with RunLoop
Most of the time when using Timers you would want your timer to run in the background while you are busy doing something else on your app. However, a normal Timer will run Synchronously on your thread. Meaning it will run only then you are already finished with your other tasks. It also only runs in your Main thread, which will pause when you begin interaction with the UI.
This is where RunLoop comes into play, Runloop will help set where on the thread do we want our Timer to run. In our case if we want to be able still loop the timer even though we are interacting with the UI. Thus, the thread we will be setting will be the RunLoop.Mode.common thread which is the thread that handles “common” input modes.
In order to add a Timer to the “common” Runloop just do the following codes:
RunLoop.current.add(timer, forMode: RunLoop.Mode.common)
Conclusion
Working with timers can be very rewarding and can add a level of depth in your app that is both fun and useful. Just be careful though! As an unmonitored timer loop can be a potential battery drainer/CPU consumer and may cause problems in the long run.
Further Reading
- The Complete Swift Tutorial for Beginners: Learn Swift programming with my Swift guide designed with the beginner in mind.
- How To Use Every Swift Loop: Swift loops allow us to repeat a block of code. Learn how to use all the types of Swift loops with this guide!
- How To Submit Your App To the App Store: Learn how to submit your app to the App Store with App Store Connect the right way!
- How to become an iOS developer: This guide will tell you what skills you should learn to become an iOS developer, where to find jobs, how to prepare for your interviews and more!