Objectively Speaking: A Crash Course in Objective-C

This is a post by iOS Tutorial Team Member Linda Burke, an indie iOS developer and the founder of canApps. Are you a software developer skilled in another platform, but want to start learning iPhone development (and hence Objective-C)? This was my situation not so long ago, and frankly, I’d gotten a bit rusty from […] By .

Leave a rating/review
Save for later
Share

Warning: Objective-C Crash Course Ahead!

Warning: Objective-C Crash Course Ahead!

This is a post by iOS Tutorial Team Member Linda Burke, an indie iOS developer and the founder of canApps.

Are you a software developer skilled in another platform, but want to start learning iPhone development (and hence Objective-C)? This was my situation not so long ago, and frankly, I’d gotten a bit rusty from moving further and further away from development in my day job.

Some two years later, I’ve created a lot of apps for the iPhone and iPad. While I often had to learn the hard way, I’d like you to be able to benefit from some of my trials and tribulations.

This tutorial is for readers who already have some programming experience. It assumes that you know your while loop from your fruit loops and a debug from a lady bug! If you’re completely new to programming, you might want to check out our iOS for High School Students series.

The goal of this tutorial is to give you confidence with some of the basics of Objective-C. Instead of taking a “let’s explain every piece of syntax” approach, we’re going to take the approach of diving right in and giving you some hands-on experience and an example to work from. It will then be a lot easier for you to consult a reference when necessary moving forward.

In this tutorial, you will create a simple app that randomly generate quotes from a stored list. In doing so, you’ll become acquainted with a number of aspects of Objective-C, including:

  • Variables
  • Arrays
  • Property lists
  • Strings
  • Predicates
  • Random selection
  • Simple interface objects and events

Let me warn you though – iPhone development with Objective-C is a lot of fun and a little addictive. Be prepared to give up some sleep, and the chores might build up! :]

Before you begin, make sure you have an Apple developer account with the provisioning details set up and the latest version of Xcode installed (you can download this for free on the Mac App Store).

When you’re done, I will (Objective) C-you after the jump! :]

Getting Started

First things first: create an Xcode project.

Start up Xcode and create a new project with the iOS\Application\Single View Application template. Then click Next.

Enter “QuoteGen” for the product name, enter your default company identifier, set device family to iPhone, and make sure Use Automatic Reference Counting is checked (but leave the other checkboxes unchecked). Now click Next and select the location to save your project.

You will notice that your project has been created with AppDelegate.h, AppDelegate.m, ViewController.h and ViewController.m files, as well as a ViewController.xib.

>

The AppDelegate contains the code that initiates the app. For this tutorial, that’s all you need to know. Here are brief explanations of the other files, with which you will be working directly:

  • ViewController.xib (XIB file for short) is the interface layout file. You visually create/design the screen that’s displayed on the iPhone device using this file.
  • ViewController.m is the interface controller class. The interface layout file is linked to this class. This happens automatically, so at this stage you don’t need to think about it other than to know that any objects or events you set up in your interface class can be linked to your interface layout very easily. This is the file that will contain the Objective-C code you’re about to create.
  • ViewController.h is the interface controller class header file, where you’ll declare the instance variables, as well as the objects and events that you need to access from the interface screen.

Note: There are two ways to create interfaces in Xcode – with XIBs and with Storyboards. Either way works fine, in this tutorial we’ll be using XIBs but if you want to try out Storyboards check out this tutorial when you’re done.

Heading in the Right Direction

Start by creating the property declarations for the variables you’ll need to store your quotes. You ought to know by now where to add these variables. Yep, the class header file, ViewController.h! Add an array as follows between the @interface and @end lines:

@property (nonatomic, retain) NSArray *myQuotes;

The property directive tells the compiler that the variable myQuotes is a property of this class. Without going too deeply into this topic – the complexities of memory management are for another day – the attributes nonatomic and retain are widely used for efficiency. The monatomic attribute specifies that the property might not work in a multi-threaded environment and retain indicates that a pointer to the specified variable will stay in memory as long as the ViewController object exists.

Note: FYI the retain keyword is synonymous with strong. In Objective-C, you used to have to do all the memory management yourself, but now with a new feature called ARC it’s automatic. To read more about ARC, check out this tutorial.

This app is also going to store some famous quotes from movies. For this, you need a second array:

@property (nonatomic, retain) NSMutableArray *movieQuotes;

Here you’re using an NSMutableArray simply to illustrate the different types of arrays. More about that later.

Manual Labor

Now you need to synthesize the arrays – this is a way to let the compiler know that it should synthesize the setter and/or getter methods for a property if you do not supply them within the @implementation block.

Do the above by editing ViewController.m and adding these two lines after the @implementation line:

@synthesize myQuotes;
@synthesize movieQuotes;

@synthesize provides default methods for getting and setting the contents of the objects. In simple terms, these methods allow you to add data to the array and retrieve it for display.

Now you can store your favorite quotes in the myQuotes array. Do this in viewDidLoad, the method that executes when the view (screen) is displayed. There’s no need to do it more than once, as the quote list won’t change, so viewDidLoad is a good place.

In viewDidLoad, add the following code after [super viewDidLoad];. Include your own favorite quotes if you like. This is the “manual labor” approach and is quite okay for a small number of array entries.

// 1 - Add array of personal quotes
self.myQuotes = [NSArray arrayWithObjects:
                      @"Live and let live", 
                      @"Don't cry over spilt milk", 
                      @"Always look on the bright side of life", 
                      @"Nobody's perfect", 
                      @"Can't see the woods for the trees",
                      @"Better to have loved and lost than not loved at all",
                      @"The early bird catches the worm",
                      @"As slow as a wet week",
                      nil];

This is the first example of calling a method. The syntax is a bit different than what you might be used to in other languages:

  • To begin calling a method, you put a bracket and then the name of the object you want to call a method on. In this case, we’re calling a (static) method on NSArray.
  • You then put the (first part) of the name of the method, and a colon. In our case, this is arrayWithObjects.
  • You then add the first parameter. This method is kinda a special case because this is a variable-length parameter method, so we can pass a list of objects to add to the array, and put nil when we’re done.
  • If the method has multiple parameters, you’d continue on in this manner. This method just has one parameter though (the list of objects).

If you’re still hung up on the syntax, don’t worry – we’ll see plenty more examples of calling methods soon.

Also notice that in Objective-C, when you use strings you put an @ symbol before them. If you’re used to other languages, this can be easy to forget, which will probably cause your app to crash :] So if your app crashes when it uses a string, double check you remembered to use the @ symbol!

SELF HELP

Use “self” when setting and getting data for a property. This is similar to the “this” keyword in other languages, and refers to the object upon which the method is running.

You can access instance variables directly (without self), but by using self you go through the getters and setters for the instance variables. Until you know learn the reasons you might want to use instance variables directly, a good rule for beginners is to always use self.

Every time you add assign to a retained property, make sure you clear it out in ViewDidUnload as follows (add the code below the existing line):

movieQuotes=nil;
myQuotes=nil;

This is important so that when the view is unloaded (which happens in low memory situations when the view is not visible), your quotes array can be freed as well. Basically you typically want to do the opposite of whatever you do in viewDidLoad. It’s a good thing to free up memory when it’s low! :]

OK, now that we have these quote arrays set up, let’s try them out!

First, declare the interface elements and actions that you’ll hook in to in the XIB file. Add the following to ViewController.h under the arrays:

@property (nonatomic, retain) IBOutlet UITextView *quote_text;

-(IBAction)quote_btn_touch:(id)sender;

The IBOutlet keyword means that quote_text is an object that can be linked to an interface element on the XIB file so that the view controller can access (or change) properties of the interface element. In this case, we’ll be setting the displayed text for the UITextView control but we could just as easily change the color, font, size, etc.

The IBAction keyword indicates that quote_btn_touch is an action that can be linked to an event for a UI control on the screen. In this case, we will be connecting to the quote button touched event.

In case you’re wondering, id means “any object that derives from NSObject”. Usually when you set up callbacks that buttons and other controls will call, they pass whatever button/control is sending the callback as the first parameter. Since we don’t necessarily know what type it is, we put id here.

Once again, you need to synthesize the new property you added. In ViewController.m, add:

@synthesize quote_text;

And don’t forget to clear out the property in ViewDidUnload:

quote_text=nil;

Now create the action method, quote_btn_touch, that is executed when the quote button is touched. Add this to the end of the file (but above @end):

-(IBAction)quote_btn_touch:(id)sender {
	// 1 - Get number of rows in array
    int array_tot = [self.myQuotes count];
	// 2 - Get random index
	int index = (arc4random() % array_tot);
	// 3 - Get the quote string for the index 
	NSString *my_quote = [self.myQuotes objectAtIndex:index];
	// 4 - Display the quote in the text view
	self.quote_text.text = [NSString stringWithFormat:@"Quote:\n\n%@",  my_quote];      
}

The arc4random function is used to generate a random number. In this case, since we want to randomly select one of the quotes, the highest possible value is the number of rows in the array, and the lowest possible value is 0. In Objective-C (like many other languages), the first row in an array is row 0, not 1.

index is just a temporary integer variable that you use to store the random number, which is then used to get that specific quote from array. As the array is a simple list of strings, you can get the quote by using objectAtIndex: and store the quote in a temporary variable of type string.

You then use the temporary string variable my_quote to set the displayed text for the quote_text control on the screen.

You use the stringWithFormat method to format the final output string so that you can display a label and add a new line before displaying the quote. It uses variable substitution, like printf in C/C++. %f is float, %d is integer, and %@ is Objective-C object.

Now in order to actually see the quote on the screen, you need to link the text field outlet in the class with a text field control in your XIB file.