Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Beginning iOS5 Development.pdf
Скачиваний:
7
Добавлен:
09.05.2015
Размер:
15.6 Mб
Скачать

192

CHAPTER 7: Tab Bars and Pickers

don’t bother with either of the arguments, and simply return the count of objects from our sole data array.

After the two data source methods, we implement one delegate method. Unlike the data source methods, all of the delegate methods are optional. The term optional is a bit deceiving, because you do need to implement at least one delegate method. You will usually implement the method that we are implementing here. However, if you want to display something other than text in the picker, you must implement a different method instead, as you’ll see when we get to the custom picker later in this chapter.

- (NSString *)pickerView:(UIPickerView *)pickerView titleForRow:(NSInteger)row

forComponent:(NSInteger)component { return [pickerData objectAtIndex:row];

}

In this method, the picker is asking us to provide the data for a specific row in a specific component. We are provided with a pointer to the picker that is asking, along with the component and row that it is asking about. Since our view has one picker with one component, we simply ignore everything except the row argument and use that to return the appropriate item from our data array.

Go ahead and compile and run again. When the simulator comes up, switch to the second tab—the one labeled Single—and check out your new custom picker, which should look like Figure 7–3.

When you’re done reliving all those Star Wars memories, come on back to Xcode and we’ll show you how to implement a picker with two components. If you feel up to a challenge, this next content view is actually a good one for you to attempt on your own. You’ve already seen all the methods you’ll need for this picker, so go ahead and take a crack at it. We’ll wait here. You might want to start off with a good look at Figure 7–4, just to refresh your memory. When you’re finished, read on, and you’ll see how we tackled this problem.

Implementing a Multicomponent Picker

The next content pane will have a picker with two components, or wheels, each independent of the other. The left wheel will have a list of sandwich fillings, and the right wheel will have a selection of bread types. We’ll write the same data source and delegate methods that we did for the single-component picker. We’ll just need to write a little additional code in some of those methods to make sure we’re returning the correct value and row count for each component.

www.it-ebooks.info

CHAPTER 7: Tab Bars and Pickers

193

Declaring Outlets and Actions

Single-click BIDDoubleComponentPickerViewController.h, and add the following code:

#import <UIKit/UIKit.h>

#define kFillingComponent 0 #define kBreadComponent 1

@interface BIDDoubleComponentPickerViewController : UIViewController

<UIPickerViewDelegate, UIPickerViewDataSource>

@property (strong, nonatomic) IBOutlet UIPickerView *doublePicker; @property (strong, nonatomic) NSArray *fillingTypes;

@property (strong, nonatomic) NSArray *breadTypes;

-(IBAction)buttonPressed;

@end

As you can see, we start out by defining two constants that will represent the two components, which is just to make our code easier to read. Components are assigned numbers, with the leftmost component being assigned zero and increasing by one each move to the right.

Next, we conform our controller class to both the delegate and data source protocols, and we declare an outlet for the picker, as well as for two arrays to hold the data for our two picker components. After declaring properties for each of our instance variables, we declare a single action method for the button, just as we did in the previous two content panes. Save this, and click BIDDoubleComponentPickerViewController.xib to open the nib file for editing.

Building the View

Select the View icon, and use the object attributes inspector to set the Bottom Bar to

Tab Bar in the Simulated Metrics section.

Add a picker view and a button to the view, change the button label to Select, and then make the necessary connections. We’re not going to walk you through it this time, but you can refer to the previous section if you need a step-by-step guide, since the two applications are identical in terms of the nib file. Here’s a summary of what you need to do:

1.Connect the doublePicker outlet on File’s Owner to the picker.

2.Connect the DataSource and Delegate connections on the picker view to File’s Owner (use the connections inspector).

3.Connect the Touch Up Inside event of the button to the buttonPressed action on File’s Owner (use the connections inspector).

Make sure you save your nib and close it before you dive back into the code. Oh, and dog-ear this page (or use a bookmark, if you prefer). You’ll be referring to it in a bit.

www.it-ebooks.info

194

CHAPTER 7: Tab Bars and Pickers

Implementing the Controller

Select BIDDoubleComponentPickerViewController.m, and add the following code at the top of the file:

#import "BIDDoubleComponentPickerViewController.h"

@implementation BIDDoubleComponentPickerViewController

@synthesize doublePicker; @synthesize fillingTypes; @synthesize breadTypes;

-(IBAction)buttonPressed

{

NSInteger fillingRow = [doublePicker selectedRowInComponent: kFillingComponent];

NSInteger breadRow = [doublePicker selectedRowInComponent: kBreadComponent];

NSString *bread = [breadTypes objectAtIndex:breadRow];

NSString *filling = [fillingTypes objectAtIndex:fillingRow];

NSString *message = [[NSString alloc] initWithFormat:

@"Your %@ on %@ bread will be right up.", filling, bread];

UIAlertView *alert = [[UIAlertView alloc] initWithTitle: @"Thank you for your order"

message:message

delegate:nil

cancelButtonTitle:@"Great!"

otherButtonTitles:nil];

[alert show];

}

.

.

.

Next, add the following lines of code to the viewDidload method:

- (void)viewDidLoad { [super viewDidLoad];

// Do any additional setup after loading the view from its nib.

NSArray *fillingArray = [[NSArray alloc] initWithObjects:@"Ham", @"Turkey", @"Peanut Butter", @"Tuna Salad", @"Chicken Salad", @"Roast Beef", @"Vegemite", nil];

self.fillingTypes = fillingArray;

NSArray *breadArray = [[NSArray alloc] initWithObjects:@"White", @"Whole Wheat", @"Rye", @"Sourdough", @"Seven Grain", nil];

self.breadTypes = breadArray;

}

www.it-ebooks.info

CHAPTER 7: Tab Bars and Pickers

195

Also, add the following lines of code to the existing viewDidUnload method:

- (void)viewDidUnload { [super viewDidUnload];

//Release any retained subviews of the main view.

//e.g. self.myOutlet = nil;

self.doublePicker = nil; self.breadTypes = nil; self.fillingTypes = nil;

}

And add the delegate and data source methods at the bottom:

.

.

.

#pragma mark -

#pragma mark Picker Data Source Methods

- (NSInteger)numberOfComponentsInPickerView:(UIPickerView *)pickerView { return 2;

}

- (NSInteger)pickerView:(UIPickerView *)pickerView numberOfRowsInComponent:(NSInteger)component {

if (component == kBreadComponent) return [self.breadTypes count];

return [self.fillingTypes count];

}

#pragma mark Picker Delegate Methods

- (NSString *)pickerView:(UIPickerView *)pickerView titleForRow:(NSInteger)row

forComponent:(NSInteger)component { if (component == kBreadComponent)

return [self.breadTypes objectAtIndex:row]; return [self.fillingTypes objectAtIndex:row];

}

@end

The buttonPressed method is a bit more involved this time, but there’s very little there that’s new to you. We just need to specify which component we are talking about when we request the selected row using those constants we defined earlier, kBreadComponent and kFillingComponent.

NSInteger breadRow = [doublePicker selectedRowInComponent: kBreadComponent];

NSInteger fillingRow = [doublePicker selectedRowInComponent: kFillingComponent];

You can see here that using the two constants instead of 0 and 1 makes our code considerably more readable. From this point on, the buttonPressed method is fundamentally the same as the last one we wrote.

www.it-ebooks.info

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]