• Skip to main content
  • Skip to primary sidebar

Ravi Shankar

Tweaking Apps

  • Swift
  • Tech Tips
You are here: Home / Develop / Simple StopWatch app in Swift

Simple StopWatch app in Swift

July 22, 2014 By Ravi Shankar 53 Comments

In this tutorial, we will see the steps for creating simple StopWatch app in Swift Programming language as shown in the below screenshot.

SimpleStopWatch demo

Click File menu -> New -> select Project from menu list.

Single View Application Xcode

Choose the template as Single View Application and click Next button.

Xcode select language as Swift

Enter name of the Product, Language as Swift then click Next to specify a folder and save the project.

Project Navigator in Xcode

Navigate to Project Navigator and select Main.storyboard. Using the Attributes Inspector, change the background colour for the ViewController to Dark Gray Colour

Attributes Inspector for View Controller

Navigate to Object Library, drag and drop UILabel to View Controller. Then align the label horizontally centred to the View Controller. Using the Attributes Inspector enter the label text as 00:00:00, change the colour to White, make the text centre aligned and increase the the font size to 27.0

Attributes Inspector for UILabel

Now drag and drop two buttons for starting and stopping the timer. Change the button text to Start and Stop respectively and set the Text Color to white.

201407221034.jpg

Now select ViewController.swift in the Project Navigator and delete the file, select Move to Trash in the Confirmation box.

201407221037.jpg201407221054.jpg

Let us add a new UIViewController file, right click on the SimpleStopWatch folder and select New File from the menu list.

201407221039.jpg

Select the template for the new file as Cocoa Touch Class (under iOS), then click Next

201407221042.jpg

Enter the name of the class as SWViewController, Subclass as UIViewController and Language as Swift. Then click Next and choose the Project folder to save the file.

201407221044.jpg

Navigate to SWViewController.swift and add a IBOutlet for UILabel.

[code language=”swift”]@IBOutlet var displayTimeLabel: UILabel!
[/code]

Then add two IBActions method for the two buttons, Start and Stop.

[code language=”swift”]
@IBAction func start(sender: AnyObject) {
}

@IBAction func stop(sender: AnyObject) {
}
[/code]

 

Navigate to Main.storyboard, select View Controller and specify the class name as SWViewController using the Identify Inspector

Identity Inspector for Class name

Now you should be able to see the IBActions and IBOutlet defined in the class file using Connection Inspector

Connections Inspector in Xcode 6

Drag and connect the UILabel with the IBOutlets, similarly connect IBActions with the buttons and specify the event as Touch Up Inside.

201407221100.jpg

Select the ViewController under View Controller Scene, click the Resolve Auto Layout Issues option and select Reset to Suggested Constraints. This would ensure that the alignment of controls remains the same for different screen size.

201407221108.jpg

Now if you try to run this project on Simulator, the screen would be as shown below. Nothing should happen on clicking the two buttons as we are yet to add the functionality.

201407221111.jpg

Write Code logic for StopWatch

Navigate to SWviewController.swift file and new function name as updateTime. This function will be used for calculating the time in minutes, seconds and fraction of milliseconds.

Add a new class level variable to the class for storing the start time.

[code language=”swift”]var startTime = NSTimeInterval()[/code]

Then add the following code in updateTime method. This is used for calculating the StopWatch time and assigning the value to the UILabel.

[code language=”swift”]</pre>
func updateTime() {

var currentTime = NSDate.timeIntervalSinceReferenceDate()

//Find the difference between current time and start time.

var elapsedTime: NSTimeInterval = currentTime – startTime

//calculate the minutes in elapsed time.

let minutes = UInt8(elapsedTime / 60.0)

elapsedTime -= (NSTimeInterval(minutes) * 60)

//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 strMinutes = String(format: "%02d", minutes)
let strSeconds = String(format: "%02d", seconds)
let strFraction = String(format: "%02d", fraction)

//concatenate minuets, seconds and milliseconds as assign it to the UILabel

displayTimeLabel.text = “\(strMinutes):\(strSeconds):\(strFraction)”

}[/code]

Add a new class level NSTimer variable as shown below.

[code language=”swift”]</pre>
var timer = NSTimer()[/code]

Navigate to Start IBAction function and add the following the code.

 

[code language=”swift”]@IBAction func start(sender: AnyObject) {
let aSelector : Selector = “updateTime”
timer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: aSelector, userInfo: nil, repeats: true)
startTime = NSDate.timeIntervalSinceReferenceDate()
}
[/code]

This would start a timer and it repeats at regular time interval of 0.01. Here we specify the “updateTime” function which gets called regularly after the specified interval. We also initialise the startTime variable to the current time. Now when the user taps on Stop button, timer is invalidated and set to nil.

[code language=”swift”]
@IBAction func stop(sender: AnyObject) {
timer.invalidate()
timer == nil
}
[/code]

If you try to run this app on the simulator, you should notice the start and stop functionality works and time is getting displayed in the Label. But the user can repeatedly tap the Start button. So when the clock is running if the user taps the Start button, clock restarts again. We can prevent this by adding the following check to start the timer only when the timer is not running.

[code language=”swift”]@IBAction func start(sender: AnyObject) {
if !timer.valid {
let aSelector : Selector = “updateTime”
timer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: aSelector, userInfo: nil, repeats: true)
startTime = NSDate.timeIntervalSinceReferenceDate()
}
}[/code]

Download the source code from here

Filed Under: Develop, ios, Programming, Xcode Tagged With: StopWatch, Swift, Xcode

Reader Interactions

Comments

  1. Trisha says

    August 1, 2014 at 6:46 pm

    Hey, awesome tutorial. I’m using Xcode 6 Beta 4 and for some reason in the function start, the line
    let aSelector : Selector = “updateTime”
    I’m getting the error “invalid character in source file” any idea why this could be?

    Reply
    • rshankar says

      August 2, 2014 at 2:45 am

      Thank you. Look likes the doubling quotes the causing this issue. Can you just retype “updateTime” and see if that resolves the issue

      Reply
  2. Steven Rosenberg says

    August 4, 2014 at 4:48 am

    Really great tutorial. I was modifying the app to provide a countdown timer. Every thing crashes when the timer reaches zero. I get an error in the statement:

    displayTimeLabel.text =…. [Exc_Bad_Instruction…]

    How might one avoid this?

    Reply
    • lio says

      September 18, 2014 at 10:26 am

      Hello Steven (and the other!), can you explain the changes of the code you did for making a countdown timer please ?

      Thanks!

      Reply
      • lio says

        September 18, 2014 at 12:22 pm

        it was simple !
        >>>
        var elapsedTime: NSTimeInterval = 5-(currentTime-startTime)

        Reply
        • rshankar says

          September 18, 2014 at 12:24 pm

          Thanks for sharing.

          Reply
          • Christian says

            November 21, 2015 at 11:07 am

            I have a problem when using the countdown, I can not make it stop at “0”. I tried many things but doesn’t work.
            Can you help me?

          • Ravi Shankar says

            November 21, 2015 at 11:17 am

            Can you share your project? Probably I can take a look.

  3. Steven Rosenberg says

    August 4, 2014 at 5:58 am

    Ah, figured it out. Had to add time.invalidate() when the timer reached zero.

    Reply
    • rshankar says

      August 4, 2014 at 1:20 pm

      Thanks for sharing the info.

      Reply
    • Mike says

      December 8, 2014 at 9:08 pm

      Where did you add the timer.invalidate() when the timer reached zero? I am not seeing how to do the test for 0 without it crashing.
      Thank You in advance!

      Reply
  4. Paul says

    August 15, 2014 at 11:25 pm

    Great tutorial! Really good resource for people just starting with Swift. I was wondering, would it be possible for you to explain why you used UInt8 constant type instead of different ones? I’m trying to understand the whole conversion into and string constants. Regards

    Reply
  5. Kiran says

    August 17, 2014 at 3:12 pm

    assertion failed: file /BinaryCache/compiler_KLONDIKE/compiler_KLONDIKE-600.0.34.4.5~1/Objects/stdlib/iphonesimulator-7.0–x86_64/stdlib/core/FloatingPoint.swift, line 1084
    (lldb)

    Implemented all that code in my own program. Kept code basically as-is.

    Reply
    • rshankar says

      August 17, 2014 at 3:57 pm

      can you post the code in line 1084.

      Reply
  6. Kiran says

    August 17, 2014 at 3:51 pm

    Also I should note that it seems like me and steven are getting the same error in different places.

    Reply
  7. xxmajia says

    August 28, 2014 at 7:59 am

    Hi, i have an compile error at this line:
    timer == nil (can not invoke ‘==’ with an argument list of type blah blah blah)
    i thought it was a mistake by i check your source code, its actually using ==

    Can you explain it a little bit? thanks

    Reply
    • rshankar says

      August 28, 2014 at 8:21 am

      Recent iOS 8 beta changes is showing this error. I think you can get rid of that line (timer == nil ). Can you please give it a try.

      Reply
  8. Arvind says

    September 7, 2014 at 5:23 am

    Awesome. It worked perfectly on Xcode 6!! Keep those coming.

    Reply
  9. Jesper Sehested says

    September 20, 2014 at 4:08 pm

    Great tutorial! Anybody know how to do, if you want the same button to be use as start and stop button?

    Reply
    • Halah says

      September 21, 2014 at 1:45 pm

      Use a boolean flag and toggle it every time the button is clicked, first true state = start timer, false state = stop timer

      Reply
      • rshankar says

        September 21, 2014 at 1:47 pm

        Thank you!!

        Reply
        • lio says

          October 14, 2014 at 10:27 pm

          Got an example if this code ?

          Reply
    • rshankar says

      September 21, 2014 at 1:50 pm

      As mentioned by Halah, you can use flag to have the same button or use tag property of the button to control the behaviour

      Reply
  10. Aborra says

    September 29, 2014 at 6:07 pm

    Hi do you know the code for a white background on swift in spritekit

    Reply
    • rshankar says

      September 30, 2014 at 4:55 am

      Sorry I haven’t worked on spritekit

      Reply
  11. Kobayashi says

    October 2, 2014 at 9:34 am

    I followed as your instruction but i had some error below :
    1. Class “SWViewController” has no initializers
    2. ‘required’ initializer ‘init(coder:)’ must be provide by subclass of ‘UIViewController’
    Im using Xcode Version 6.0.1 (6A317)

    Thanks so much

    Reply
    • rshankar says

      October 3, 2014 at 4:40 pm

      Setting the IBOutlet with ! should fix the problem. Could you please try this. @IBOutlet var displayTimeLabel: UILabel!

      Reply
  12. Kobayashi says

    October 5, 2014 at 3:10 am

    thanks rshankar.
    But this error involve to NSTimer var , when i delete this var, error was disappeared.
    Can you got this problem before?

    Reply
    • rshankar says

      October 5, 2014 at 3:12 am

      I haven’t come across this problem before.

      Regards,
      Ravi

      Reply
  13. hja says

    October 11, 2014 at 4:51 am

    /how i add the ‘clear’ function for this?
    can you show your code..?

    Reply
  14. MarcoAlmeida says

    October 31, 2014 at 4:31 am

    Great tutorial!!! I tried to add Hours to your example and it worked, but when the label displays the first hour the minutes does not goes to zero, it keeps counting to 6-, 61, 62 and so on.

    So, do you have any idea of how I could implement a complete timer with hours:minutes:seconds:milliseconds?

    Thanks and Best Regards!!!

    Reply
  15. Atharva says

    November 2, 2014 at 6:14 pm

    Hey, I’m building a stopwatch that displays hours, minutes and seconds. The problem is when the minutes reach 60 they don’t reset to 0 they keep on going to 61,62… How can I fix that?

    Can you explain this line of code:

    let strMinutes = minutes > 9 ? String(minutes):“0” + String(minutes)
    let strSeconds = seconds > 9 ? String(seconds):“0” + String(seconds)
    let strFraction = fraction > 9 ? String(fraction):“0” + String(fraction)

    Thanks!

    Reply
  16. sunny says

    November 19, 2014 at 3:15 am

    Hi Sahankar,
    thanks for the tutorial, everything works finr for me except the one thing.
    while time is running, if i pause the time, when i press the play button to resume the pause, its starts from

    Reply
  17. Marko says

    January 30, 2015 at 10:01 am

    After stoping the timer, when i press play, it restarts from 0. How could i make the timer resume after stoping it?

    Reply
  18. fustav says

    February 5, 2015 at 12:30 pm

    Hello, I need to implement a Timer that log out the user – for security reason – after 3minutes of inactivity.

    How can I handle it with timer and selectors?
    maybe touchesBegan(…)

    Thank you

    Reply
  19. Frank says

    February 15, 2015 at 12:01 am

    Hi Sahankar,
    just a question. I’ve use your example into my project, but when i start iphone 5/5s simulator it work great, but if i start iphone 4S/iPad Retina…it fail with this error:

    fatal error: floating point value can not be converted to UInt8 because it is greater than UInt8.max

    Where is my errors?

    Reply
  20. David Elvekjær says

    March 24, 2015 at 1:08 pm

    Hey,

    Thanks for a great tutorial, I added a bit functionality, so it can pause and reset timer. Just need to add the connection to the startButton outlet

    https://www.dropbox.com/s/dufvkv909ezz7nu/SWViewController.swift?dl=0

    Reply
    • Krishna Thakur says

      February 2, 2016 at 2:12 pm

      Hello sir in your modified code
      you have used same button for start and pause and continue. But in my case i have three separate button when i click on continue it is not continuing timer. i have used these line in resume button.

      startButton.setTitle(“Continue”, forState: UIControlState.Normal)
      elapsedTime += startTimeDate.timeIntervalSinceNow
      timer.invalidate()

      can you help me please.

      Reply
  21. Brandon says

    April 23, 2015 at 6:40 pm

    Great tutorial! How do you get the elapsed time for hours, if we wanted to add hours to our stop watch?

    Thank you!

    Reply
  22. Jordan says

    April 29, 2015 at 12:59 pm

    why do we need to delete the ViewController.Swift?? Can anyone explain? Thanks in advance!

    Reply
    • rshankar says

      April 29, 2015 at 1:08 pm

      Thanks for bringing up this question. It was done to have viewcontroller with a different name instead of using the default view controller. You can very well use ViewController.swift or change the viewcontroller and the corresponding class name instead of deleting the file.

      Hope this clarifies your doubt.

      Reply
  23. preethi says

    May 29, 2015 at 3:30 pm

    Can I get the tutorial for hh:mm:ss
    in swift ?

    Reply
  24. Gabor says

    June 9, 2015 at 2:55 pm

    it is painful to see such solution in a tutorial:

    let strMinutes = minutes > 9 ? String(minutes):“0” + String(minutes)

    while we have:

    let strMinutes = String(format: “%02d”, minutes)

    Reply
    • rshankar says

      June 9, 2015 at 3:18 pm

      Thanks for the feedback. Updated the tutorial with more clean code now.

      Reply
  25. Charlotte says

    June 16, 2015 at 7:28 am

    I’d like to produce an audible sound when the timer reaches the end. Can you suggest code for this?

    Great tutorial. Many thanks

    Reply
    • rshankar says

      June 16, 2015 at 7:48 am

      Can you try AVAudio tutorial – https://rshankar.com/how-to-record-and-play-sound-in-swift/

      Reply
  26. Charlotte says

    June 18, 2015 at 12:29 pm

    Thanks!

    Reply
  27. AJ says

    July 24, 2015 at 6:00 pm

    Hi, is there a way to do the exact same thing however have the current time viewed and it is ticking as a digital clock? I would appreciate an answer thank you!!

    Reply
  28. boris says

    August 21, 2015 at 5:07 pm

    //
    // SWViewController.swift
    // StopWatch
    //
    // Created by Mac Owner on 8/21/15.
    // Copyright (c) 2015 Mac Owner. All rights reserved.
    //

    import UIKit

    class SWViewController: UIViewController {

    override func viewDidLoad() {
    super.viewDidLoad()

    // Do any additional setup after loading the view.
    }

    override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()
    // Dispose of any resources that can be recreated.
    }

    /*
    // MARK: – Navigation

    // In a storyboard-based application, you will often want to do a little preparation before navigation
    override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
    // Get the new view controller using segue.destinationViewController.
    // Pass the selected object to the new view controller.
    }
    */

    }

    @IBOutlet var displayTimeLabel: UILabel!
    @IBAction func start(sender: AnyObject) {
    }

    @IBAction func stop(sender: AnyObject) {
    }
    can someone please correct my code i am using Xcode 6.4

    Reply
  29. Michael says

    August 29, 2015 at 7:05 am

    Great tutorial! I was just wondering if you (or someone else!) could explain the line “elapsedTime -= NSTimeInterval(seconds)” and the similar lines. I’m having a hard time understanding what’s happening here.

    Reply
  30. Eugene Tartakovsky says

    November 7, 2015 at 7:05 pm

    Hello Ravi!

    Thanks for the great tutorial. I was solving the same problem together and your guide helped me a lot.

    Also i’ve found interesting answer on stackoverflow:
    http://stackoverflow.com/questions/31375361/format-realtime-stopwatch-timer-to-the-hundredth-using-swift

    Combining your guide and this answer i’ve written a reusable and optimized Stopwatch class for my application.

    I decided i should share it with you and your audience because it is assembled from public sources and with your contribution to it. Here it is:
    https://gist.github.com/Flar49/06b8c9894458a3ff1b14

    Hope it’ll help. Thanks again 🙂

    Reply
  31. Kegham Karsian says

    December 7, 2016 at 5:58 pm

    Thanks Ravi. A great professional tutorial. I wanted to know if it is possible to use a custom startTime TimeInterval like 07:46:10 to create a count down timer from this start time instead of a stop watch that increments.

    Reply
  32. Appu Yaragal says

    July 11, 2018 at 8:17 am

    Hi, This is nice tutorial. But I have one doubt here How to do the resume timer. When a timer is running, I have to stop the timer, but I have to start same time like a resume, I dont need to again start time(current time). can you help me achieve this task.

    Reply

Leave a Reply Cancel reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Primary Sidebar

TwitterLinkedin

Recent Posts

  • How to block keywords in Jio broadband
  • How to disable opening an app automatically at login in Mac
  • How to set preferred Wifi network on Mac
  • Attribute Unavailable: Estimated section warning before iOS 11.0
  • How to recover Firefox password from Time Machine backup

Pages

  • About
  • Privacy Policy
  • Terms and Conditions

Copyright 2022 © rshankar.com

Terms and Conditions - Privacy Policy