The controller manages the communication between the view and the model. It takes the data from the model and communicates it to the view for display.
In the same vein, the controller also takes the changed data (due to user interaction or something else) and communicates it back to the model.
Say SmoothiesViewController and EditRecipeViewController need to communicate with each other.
Declare Protocol and use delegate variable
First declare protocol like this:
EditRecipeViewController.h
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 |
@class EditRecipeViewController; /* * The delegate for EditRecipeViewController. */ @protocol EditRecipeDelegate <NSObject> - (void)editRecipeDidSave:(EditRecipeViewController*)controller; @optional - (void)editRecipeDidCancel:(EditRecipeViewController*)controller; @end /* * The screen that lets you add a new recipe or edit an existing recipe. */ @interface EditRecipeViewController : UIViewController < UINavigationControllerDelegate, UIImagePickerControllerDelegate > { UIImagePickerController* imagePicker; } //@property blah blah // Our delegate object @property (nonatomic, assign) id<EditRecipeDelegate> delegate; //methods blah blah @end |
Once your protocol is set. You declare a delegate:
1 |
@property (nonatomic, assign) id<EditRecipeDelegate> delegate; |
Whoever conforms to that delegate MUST implement the methods in that protocol. Because this class with the delegate, will be calling these methods, and the classes that conform to this protocol, must execute these methods.
In EditRecipeViewController.m it is used like this:
1 2 3 4 5 6 7 8 |
- (IBAction)cancel { // Notify the delegate if it implements the optional method if ([self.delegate respondsToSelector:@selector(editRecipeDidCancel:)]) [self.delegate editRecipeDidCancel:self]; [self.parentViewController dismissModalViewControllerAnimated:YES]; } |
First, we check to see if our delegate responds to such method. If it does, then call it. This means that ALLLLL the UIViewControllers that conforms to our EditRecipeDelegate protocol must execute their method of editRecipeDidCancel.
UIViewController conforms to protocol
Say SmoothiesViewController conforms to our EditRecipeDelegate
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
#import "EditRecipeViewController.h" @class DataModel; /* * This is the view controller that lists all smoothie recipes. */ @interface SmoothiesViewController : UITableViewController <EditRecipeDelegate> { } // We have a weak reference to the shared Data Model object @property (nonatomic, assign) IBOutlet DataModel* dataModel; - (IBAction)addRecipe; @end |
This means in our SmoothiesViewController.m file, we must implement the required protocol methods:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
#pragma mark - #pragma mark EditRecipeDelegate - (void)editRecipeDidSave:(EditRecipeViewController*)controller { // Create a new Recipe object with the values from the controller // and add it to the data model Recipe* recipe = [[Recipe alloc] init]; recipe.name = controller.name; recipe.instructions = controller.instructions; recipe.image = controller.image; [self.dataModel addRecipe:recipe]; [recipe release]; // Refresh the table [self.tableView reloadData]; } |