iPhone Programming : Table-View-Based Applications - Connecting the Controller to the Model

2/6/2011 4:20:02 PM
Now that we’ve built the model, we have to go back to the RootController class and build the bridge between the view controller and the model. To do this we need to make only one change in the RootController interface declaration (RootController.h). Add a pointer to an NSMutableArray that you’ll then populate inside the viewDidLoad: method:
@interface RootController : UIViewController
<UITableViewDataSource, UITableViewDelegate> {
UITableView *tableView;
NSMutableArray *cities;

Changes to the implementation (RootController.m) are only slightly more extensive. You need to #import both the City.h and CityGuideDelegate.h interface files, as you’ll be using both of these classes inside the updated implementation:

#import "RootController.h"
#import "CityGuideDelegate.h"
#import "City.h"

As I mentioned earlier, you must implement the viewDidLoad: method. This UIViewController method is called after the controller’s view is loaded into memory, and is the method we’ll normally use to set up things that the view needs. You’ll find that the Xcode template included a stub for viewDidLoad (not far from the #pragma mark-labeled instance methods), but it’s commented out (wrapped inside a comment, so it doesn’t compile). Replace it with the following (be sure to remove the /**/ so that it’s no longer commented out): and

- (void)viewDidLoad {
CityGuideDelegate *delegate =
(CityGuideDelegate *)[[UIApplication sharedApplication] delegate];
cities = delegate.cities;

Here, we acquired a reference to the application delegate by using the [[UIApplication sharedApplication] delegate] method call. Since this method returns a generic id object, we had to cast it to be a CityGuideDelegate object before assigning it. We then grabbed a pointer to the array of cities managed by the app delegate.

Since our code now declares a new variable, we also have to remember to release it in the dealloc: method:

- (void)dealloc {
[tableView release];
[cities release];
[super dealloc];

Finally, we must use the model to populate the table view. The number of rows in the table view should now be determined by the number of cities in the NSMutableArray instead of simply returning “3” all the time. We must now go ahead and change the tableView: numberOfRowsInSection: method to reflect that by replacing the line return 3; (and the comment above it). Here’s how the method should look now:

- (NSInteger)tableView:(UITableView *)tv
return [cities count];

Finally, we need to change the tableView:cellForRowAtIndexPath: method to label the cell with the correct city name. To do this, add the following code shown in bold, which figures out which row of the table we’re trying to populate and looks up the appropriate element of the cities array:

- (UITableViewCell *)tableView:(UITableView *)tv
cellForRowAtIndexPath:(NSIndexPath *)indexPath
UITableViewCell *cell =
[tv dequeueReusableCellWithIdentifier:@"cell"];
if( nil == cell ) {
cell = [[[UITableViewCell alloc]
initWithFrame:CGRectZero reuseIdentifier:@"cell"] autorelease];

City *thisCity = [cities objectAtIndex:indexPath.row];
cell.textLabel.text = thisCity.cityName;
return cell;

We’ve now reached a point where we have a functional, buildable application. However, while our table view now reflects our model, we still can’t access any of the information we entered about our cities. When we click on a city we want the application to tell us about the city, and for that we need to modify the tableView:didSelectRowAtIndexPath: method. But for now, click the Build and Run button on the Xcode toolbar, and your iPhone Simulator should pop up, looking like Figure 1.

1. Mocking Up Functionality with Alert Windows

Before I go on to show how to properly display the city descriptions and images using the UINavigationController class, let’s do a quick hack and get the application to pop up an alert window when we click on a table view cell. Go back to RootController.m and add the highlighted lines in the following code to the didSelectRowAtIndexPath: method:

- (void)tableView:(UITableView *)tv
didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
City *thisCity = [cities objectAtIndex:indexPath.row];
UIAlertView *alert = [[UIAlertView alloc]
initWithTitle:thisCity.cityName message:thisCity.cityDescription
delegate:self cancelButtonTitle:nil otherButtonTitles:@"OK", nil];
[alert show];
[alert autorelease];

[tv deselectRowAtIndexPath:indexPath animated:YES];

Figure 1. Populating the UITableView of our application using the new model

In this method, we create a UIAlertView window with an OK button, and set the title to be the city name and the contents to be the city description. You can see how this looks in Figure 2.

Figure 2. After you modify the tableView:didSelectRowAtIndexPath: method, a UIAlertView pop up appears when you click on a city name

  •  Programming the Mobile Web : Mobilizing WordPress and Other CMSs
  •  Programming the Mobile Web : Server-Side Browser Detection and Content Delivery - Content Adaptation
  •  Programming the Mobile Web : Multimedia and Streaming
  •  Mobile Application Security : BlackBerry Security - Development and Security Testing
  •  Mobile Application Security : BlackBerry Security - Introduction to Platform
  •  Windows Phone 7 Development : Using a WebBrowser Control to Display Dynamic Content
  •  Windows Phone 7 Development : Using a WebBrowser Control to Display Local HTML Content
  •  Windows Mobile Security - Networking
  •  Windows Mobile Security - Local Data Storage
  •  Windows Mobile Security - Permissions and User Controls
  •  Windows Phone 7 Development : Using a WebBrowser Control to Display Web Content
  •  Windows Phone 7 Development : Adding a WebBrowser Control
  •  Programming the Mobile Web : Content Delivery (part 3)
  •  Programming the Mobile Web : Content Delivery (part 2) - File Delivery
  •  Programming the Mobile Web : Content Delivery (part 1) - Defining MIME Types
  •  iPhone Application Development : Using Switches, Segmented Controls, and Web Views (part 3)
  •  iPhone Application Development : Using Switches, Segmented Controls, and Web Views (part 2)
  •  iPhone Application Development : Using Switches, Segmented Controls, and Web Views (part 1)
  •  iPhone Application Development : Using Advanced Interface Objects and Views - User Input and Output
  •  Windows Phone 7 Development : Wiring Up Events to an Application Bar ( part 2)
    Top 10
    Nikon 1 J2 With Stylish Design And Dependable Image And Video Quality
    Canon Powershot D20 - Super-Durable Waterproof Camera
    Fujifilm Finepix F800EXR – Another Excellent EXR
    Sony NEX-6 – The Best Compact Camera
    Teufel Cubycon 2 – An Excellent All-In-One For Films
    Dell S2740L - A Beautifully Crafted 27-inch IPS Monitor
    Philips 55PFL6007T With Fantastic Picture Quality
    Philips Gioco 278G4 – An Excellent 27-inch Screen
    Sony VPL-HW50ES – Sony’s Best Home Cinema Projector
    Windows Vista : Installing and Running Applications - Launching Applications
    Most View
    Bamboo Splash - Powerful Specs And Friendly Interface
    Powered By Windows (Part 2) - Toshiba Satellite U840 Series, Philips E248C3 MODA Lightframe Monitor & HP Envy Spectre 14
    MSI X79A-GD65 8D - Power without the Cost
    Canon EOS M With Wonderful Touchscreen Interface (Part 1)
    Windows Server 2003 : Building an Active Directory Structure (part 1) - The First Domain
    Personalize Your iPhone Case
    Speed ​​up browsing with a faster DNS
    Using and Configuring Public Folder Sharing
    Extending the Real-Time Communications Functionality of Exchange Server 2007 : Installing OCS 2007 (part 1)
    Google, privacy & you (Part 1)
    iPhone Application Development : Making Multivalue Choices with Pickers - Understanding Pickers
    Microsoft Surface With Windows RT - Truly A Unique Tablet
    Network Configuration & Troubleshooting (Part 1)
    Panasonic Lumix GH3 – The Fastest Touchscreen-Camera (Part 2)
    Programming Microsoft SQL Server 2005 : FOR XML Commands (part 3) - OPENXML Enhancements in SQL Server 2005
    Exchange Server 2010 : Track Exchange Performance (part 2) - Test the Performance Limitations in a Lab
    Extra Network Hardware Round-Up (Part 2) - NAS Drives, Media Center Extenders & Games Consoles
    Windows Server 2003 : Planning a Host Name Resolution Strategy - Understanding Name Resolution Requirements
    Google’s Data Liberation Front (Part 2)
    Datacolor SpyderLensCal (Part 1)