Welcome to Day 28 of the 31 Days of iOS. Yesterday, we wrapped up a two part mini-series on Push Notifications. Since getting set up for push notifications is so complicated, we had to split that into a separate entry from the code part of it. Today we’re going to talk about something that impacts many of the other entries in the series: showing activity indicators. If you’re performing long running network communication or doing any other sort of backend processing, you’ll want to make sure the user knows something is going on. This is often done with a progress indicator of some kind. Any time you’ve seen the spinning color wheel in OS X or the hourglass in Windows, you’ve been looking at an activity indicator. We’ll be starting with a brand new project, but if you’d like to follow along with the completed code, you can access it here.
Creating our project
Open up Xcode and choose File, New, Project. We’ll use a Single View Application and name it DayTwentyEight:
We’re going to use a very simplified UI today. We are only going to add a single button for now. Open up MainStoryboard.storyboard and drag a round rect button from the UI element selector in the bottom right on to your view. When you’re done, your UI will look like this:
Open up the Assistant Editor in the top right of Xcode and control + drag and drop from the button to your code behind to create a new action. After adding it, your ViewController.h will look like this:
Now we can implement a long running process.
A long running process
We took a pretty long look at background threads and processes in day 23 so we’re going to glaze over a few things here. Specifically, I’m not going to explain how the background thread works but will explain what’s going on. First we’ll implement the tappedProcessStuff method:
Essentially we’re spinning up a background thread which does a few seconds worth of sleeping. Once that is done, we then call the backgroundDone method on the main (UI) thread. In the backgroundDone method we’re just going log something for now:
Now run the app. You should see that it’s possible for you to tap the button again and again and again. This will start up several background processes which isn’t really what we want. We don’t want to lock the UI and prevent but we do want to let the user know that something is happening with the app. Enter the progress indicator.
Adding a progress indicator
First let’s open back up MainStoryboard.storyboard. Drag an Activity Indicator View from the UI element selector on to the center of the view:
Before we change to do anything in the code side, let’s hide the indicator when it’s not in use. Click on the activity indicator and open the Attributes Inspector in the top right of Xcode. You’ll want to check the Hides When Stopped and Hidden boxes:
Now flip over to the Assistants Editor and control + click and drag from the activity indicator to your code behind to create an outlet. When you’re done, your header will look like this:
Now we can use the activity indicator from the code behind.
Animating the activity indicator
Open up ViewController.m and go to the tappedProcessStuff method. We just need to make a simple one line change:
We’re calling startAnimating on our indicator. This works because we’re doing the extensive processing in a background thread. If we got rid of the background part and did the loop immediately after the call to startAnimating it wouldn’t work. The reason for this is that control has to be returned to the UI thread in order for the animation to start. Now, we make a similar one line change to the backgroundDone method:
We just call stopAnimating on our indicator to make it stop and hide (since we told it to hide when stopped). Now when you run your app and tap the Process Stuff button, you’ll see the indicator animating:
Now let’s talk about another way to indicate things are going on.
Network Activity Indicator
iOS users are use to being told when things are going on. This can be done with the activity indicator as we did above, but we can also do it with a Network Activity Indicator. Just like we started and stopped animating the indicator with a single line, we can do the same for the network indicator with a single line. To start it, we call this:
[UIApplication sharedApplication].networkActivityIndicatorVisible = TRUE;
And to turn it off, we would call this:
[UIApplication sharedApplication].networkActivityIndicatorVisible = FALSE;
Now when we run the app, we’ll see a little indicator appear in the black bar at the top of the iPhone by the wifi signal:
The last topic we’re going to cover today is the progress bar. To do this, start by returning to MainStoryboard.storyboard. This time we’re going to drag a Progress View onto our view:
Open up the Assistant editor and control + click and drag from the progress view to your code behind. When you’re done, it will look like this:
Now we can switch over to ViewController.h. Our first change will be to the tappedProcessStuff method:
The only change here is that inside of the loop, we’ve added a call to a new method, updateProgressBar. This call is being made the same way we call the backgroundDone method when the loop is finished, on the main UI thread. We’re also passing in the current count. Now let’s look at the updateProgressBar method:
Here, we’re calculating a progress point by dividing the count by 100.0 (we have to use .0 in order to get the float out). We can then call setProgress on the progress view with that value. Now when you run your app, you should see the progress bar go from empty to filled in time with the loop.
Today we looked at several different ways to show users that things are happening and progress is occuring. Remember that it’s very important for users to know what’s happening with their device. If they don’t understand that things are happening behind the scenes, they might not find your app very intuitive or understandable. Also, always remember to hide or remove or turn off the indicators when you’re done with them. You can download the completed code from today’s walkthrough here.