Delegate in Objective-C - ios

I am new at Objective-C, and I'm trying to understand delegates. I have searched and read a lot, but nothing is really helping me understand. I think that best way to understand this might be asking a question with a sample app.
I'm trying to create a grade calculator application to test my skills. Here are my files:
mainTableViewController.h
#import <UIKit/UIKit.h>
#interface mainTableViewController : UITableViewController
#end
mainTableViewController.m
#import "mainTableViewController.h"
#import "addLectureViewController.h"
#interface mainTableViewController ()
#end
#implementation anaTableViewController
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
[lectureName count];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
return cell;
}
#end
addLectureViewController.h
#import <UIKit/UIKit.h>
#interface addLectureViewController : UIViewController
#property (weak, nonatomic) IBOutlet UITextField *lectureNameTextField;
- (IBAction)addButtonPressed:(id)sender;
#property NSMutableArray *lectureName;
#property NSObject *lecture;
#end
addLectureViewController.m
#import "addLectureViewController.h"
#interface addLectureViewController ()
#end
#implementation addLectureViewController
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
_lectureName = [[NSMutableArray alloc] init];
_lecture = [[NSObject alloc] init];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
}
- (IBAction)addButtonPressed:(id)sender {
_lecture = _lectureNameTextField.text;
[_lectureName addObject:_lecture];
NSLog(#"%#",_lectureName);
}
#end
Everything is okay so far. But when i try to use the _lectureName NSMutableArray at mainTableViewController.m, I can't see the array.
I know the codes for printing the array in tableView. I know they are not at there right now. I just don't understand implement delegate codes to my code.

If You want to display something on the rows of the table, You can take an NSArray and you have to return the count of the array in the delegate method:
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return array.count;
}
Otherwise, table will not display any elements. And delegate method cellForRowAtIndexPath will only be called if you are returning a particular array count of number count in your numberOfRowsInSection method.
You can take reference from these links to understand delegates:
http://www.tutorialspoint.com/ios/ios_delegates.htm
How do I set up a simple delegate to communicate between two view controllers?
http://code.tutsplus.com/tutorials/ios-sdk-custom-delegates--mobile-10848
But in the case of tableView, the delegate methods are internally defined and triggered internally. We just need to set those delegates to the controller which acts as a listener.

The below code might have syntax errors but they can provide a summary of delegates for this code.
Make the following changes :-
mainTableViewController.h
#import <UIKit/UIKit.h>
#interface mainTableViewController : UITableViewController
#property(strong, nonatomic) NSMutableArray *lectureName
#end
Synthesize the property lectureName in mainTableViewController.m
Then make the following changes in addLectureViewController.h
#import <UIKit/UIKit.h>
#import "mainTableViewController.h"
#interface addLectureViewController : UIViewController
#property (weak, nonatomic) IBOutlet UITextField *lectureNameTextField;
- (IBAction)addButtonPressed:(id)sender;
#property(weak, nonatomic) id<mainTableViewController> delegate;
#property NSMutableArray *lectureName;
#property NSObject *lecture;
#end
Synthesize the property delegate in addLectureViewController.m
Then make the following change :-
- (IBAction)addButtonPressed:(id)sender {
_lecture = _lectureNameTextField.text;
[_lectureName addObject:_lecture];
NSLog(#"%#",_lectureName);
delegate.lectureName=_lectureName;
}
Assuming that you are pushing addLectureViewController from mainTableViewController, also include the following code in prepareForSegue of mainTableViewController (or whatever method in which you are pushing addLectureViewController). :-
addLectureViewController *vc=[[addLectureViewController alloc] init];
vc.delegate=self;
// Push vc
The above code actually creates a weak property of type id<mainTableViewController> called delegate (weak in order to prevent reference cycles). This way, addLectureViewController can update mainTableViewController's property.

Points:
Why is the class in mainTableViewController.m named anaTableViewController. It should be mainTableViewController (almost always, until you get more advanced).
mainTableViewController and addLectureViewController should start with capital letters.
The only way for mainTableViewController to access lecture is through a addLectureViewController object, e.g.
addLectureViewController *alvc = // *something* here
NSArray *localLecture = [alvc lecture];
Figure out how you have access to an addLectureViewController and you will have solved your problem.

Related

Custom UITableViewCell without dequeueReusableCellWithIdentifier

So I have a custom UITableViewCell:
TestTableViewCell.h
#import <UIKit/UIKit.h>
#interface TestTableViewCell : UITableViewCell
#property (strong, nonatomic) IBOutlet UILabel *testCellLabel;
#end
TestTabelViewCell.m
#import "TestTableViewCell.h"
#implementation TestTableViewCell
-(id)initWithCoder:(NSCoder *)aDecoder {
self = [super initWithCoder:aDecoder];
if (self) {
_testCellLabel = [[UILabel alloc] init];
}
return self;
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
#end
And then I have view controller with a table view that uses the custom table view cell. However this issue is that I don't want to use dequeueReusableCellWithIdentifier within the cellForRowAtIndexPath. I instead want to have an array of cells.
ViewController.h
#import <UIKit/UIKit.h>
#interface ViewController : UIViewController <UITableViewDataSource, UITableViewDelegate>
#end
ViewController.m
#import "ViewController.h"
#import "TestTableViewCell.h"
#interface ViewController ()
#property (weak, nonatomic) IBOutlet UITableView *tableView;
#property (strong, nonatomic) NSArray *myTableViewCells;
#end
#implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (NSArray *)myTableViewCells {
TestTableViewCell *cell1 = [[TestTableViewCell alloc] init];
cell1.testCellLabel.text = #"one";
cell1.backgroundColor = [UIColor blueColor];
TestTableViewCell *cell2 = [[TestTableViewCell alloc] init];
cell2.testCellLabel.text = #"two";
cell1.backgroundColor = [UIColor greenColor];
if (!_myTableViewCells) {
_myTableViewCells = #[cell1, cell2];
}
return _myTableViewCells;
}
#pragma mark - UITableView delegate functions
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return self.myTableViewCells.count;
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
TestTableViewCell *cell = self.myTableViewCells[indexPath.row];
return cell;
}
#end
The problem is that there is no testCellLabel appearing in the table view cell. I know the cells are there, because I set their background colour.
After talking to a few people, apparently I need to do some sort of loading from the XIB or the NIB for the UI to load properly? Even though the label is defined in the cell in the storyboard.
I know this is going against the norm and that Apple really wants you to use dequeueReusableCellWithIdentifier, but I know it won't work in the situation I need it in. I have done the reading on that much so please don't just tell me to use it. This code example is just very basic for example sake and ease of use.
Any help would be greatly appreciated.
TestTableViewCell *cell1 = [[TestTableViewCell alloc] init];
Creates a new TestTableViewCell object and does not instantiate it from the storyboard like you're thinking it does. Therefor all outlets created will be nil and simply not show up. The fact that you can set the background colour is not evidence that your implementation works.
You need to use dequeueReusableCellWithIdentifier. You say that it doesn't work for your problem.. show me how it doesn't work and I will tell you why you're wrong.
Edit
I see in your comments you say your cell needs a custom setter. Well, when you use dequeueReusableCellWithIdentifier you can do all setup work in awakeFromNib (If using a xib file) OR initWithCoder if you are using the storyboard.
You can create cell without dequeueResableCellWithIdentifer.
[[UITableViewCell alloc]initWithStyle:<#UITableCellStyle#> resueIdentifier:<#(nullable *NSString)#>]

How to pass message using delegates from one view controller to another using delegate?

main storyboard imageI have one Table View Controller named "Contacttableviewcontroller" and one View Controller as"Detailviewcontroller". I have 2 text fields in my View Controller to give contact name and number. I have a button to save. When I click on that button, it should display it in Table View Controller. Concept I am using is passing information from destination to source using delegates. Here goes my code which is not working properly.
Detailviewcontroller.h
#protocol detailviewcontrollerdelegate<NSObject>
- (void)additem:(NSString *)Name MOBILE:(NSString *)Mobile;
#end
#interface DetaiViewController : UIViewController
#property (weak, nonatomic) IBOutlet UITextField *nametextfield;
#property (weak, nonatomic) IBOutlet UITextField *mobiletextfield;
- (IBAction)Save:(id)sender;
#property(nonatomic,weak)id<detailviewcontrollerdelegate>delegate;
Detailviewcontroller.m
- (IBAction)Save:(id)sender {
[self.delegate additem:self.nametextfield.text MOBILE:self.mobiletextfield.text];
}
Contacttableviewcontroller.h
#interface ContactTableViewController : UITableViewController<detailviewcontrollerdelegate>
#property(strong,nonatomic)NSString *contactname;
#property(strong,nonatomic)NSString *contactno;
-(void)reloadtabledata;
#property(strong,nonatomic)NSArray *contactnamearray;
#property(strong,nonatomic)NSArray *contactnoarray;
#end
Contacttableviewcontroller.m
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return 4;
}
- (void)additem:(NSString *)Name MOBILE:(NSString *)Mobile
{
self.contactname=Name;
self.contactno=Mobile;
self.contactnamearray=#[self.contactname];
self.contactnoarray=#[self.contactno];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"cellreuse" forIndexPath:indexPath];
cell.textLabel.text=[_contactnamearray objectAtIndex:indexPath.row];
cell.detailTextLabel.text=[_contactnoarray objectAtIndex:indexPath.row];
return cell;
}
-(void)reloadtabledata
{
[self.tableView reloadData];
}
Firstly, you need to check, if you have attached your action method, -Save: to your button or not. You can attach it through the storyboard or programatically. To do it through storyboard, give your button a name like saveButton(not compulsory) and then attach it by ctrl dragging as usual.
Make sure, you attach all the IBOutlets through storyboard properly.
P.S: I have updated the variable's name with proper naming convention. You should also follow the camel case convention while naming your variables.
here is the DetailViewController.h code-
#import <UIKit/UIKit.h>
#protocol DetailViewControllerDelegate;
#interface DetailViewController : UIViewController
#property (weak, nonatomic) IBOutlet UITextField *nameTextField;
#property (weak, nonatomic) IBOutlet UITextField *mobileTextField;
#property(strong, nonatomic) IBOutlet UIButton *savebutton;
- (IBAction)Save:(id)sender;
#property(nonatomic,weak)id<DetailViewControllerDelegate>delegate;
#end
#protocol DetailViewControllerDelegate<NSObject>
- (void)additem:(NSString *)Name MOBILE:(NSString *)Mobile;
#end
And DetailViewController.m-
#import "DetailViewController.h"
#interface DetailViewController ()
#end
#implementation DetailViewController
- (void)viewDidLoad {
[super viewDidLoad];
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
- (IBAction)Save:(id)sender {
[self.delegate additem:self.nameTextField.text MOBILE:self.mobileTextField.text];
[self.navigationController popToRootViewControllerAnimated:YES];
}
#end
Now, if you put a break point inside your action method, you will see, it is getting called.
You can see an extra line of code-
[self.navigationController popToRootViewControllerAnimated:YES];
-this is making sure that when you press the save button, it not only sends the data, but also returns to you TableView Controller to show your results.
Now, you need to make sure that your DetailViewController knows who is going to implement its delegate. So, in your ContactTableViewController, wherever, you are initialising your DetailViewController, you have to assign its delegate to self.
So, after a little tweaks, the ContactTableViewController.h class looks like-
#import <UIKit/UIKit.h>
#import "DetailViewController.h"
#interface ContactTableViewController : UITableViewController<DetailViewControllerDelegate>
#property(strong,nonatomic)NSString *contactName;
#property(strong,nonatomic)NSString *contactNo;
-(void)reloadtabledata;
#property(strong,nonatomic)NSMutableArray *contactNameArray; //need to be mutable array, so that the data can keep appending
#property(strong,nonatomic)NSMutableArray *contactMobileNoArray; //same as above
#end
Now, there are some small modifications in the file but, the comments should clarify the purpose.
So, the ContactTableViewController.m file looks like
#import "ContactTableViewController.h"
#interface ContactTableViewController ()
#end
#implementation ContactTableViewController
- (void)viewDidLoad {
[super viewDidLoad];
//Make sure you initialize the array before tryig to add any element
self.contactNameArray =[[NSMutableArray alloc]init];
self.contactMobileNoArray=[[NSMutableArray alloc]init];
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
#pragma mark-
#pragma mark- TableView Datasource methods
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return [self.contactNameArray count]; //you need to set the row count as the same as the array elements
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"cellreuse" forIndexPath:indexPath];
cell.textLabel.text=[self.contactNameArray objectAtIndex:indexPath.row];
cell.detailTextLabel.text=[self.contactMobileNoArray objectAtIndex:indexPath.row];
return cell;
}
-(void)reloadtabledata
{
[self.tableView reloadData];
}
#pragma mark- Segue method
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
[segue.destinationViewController setTitle:#"Add Details"];
DetailViewController *vc = [segue destinationViewController];
vc.delegate=self; // By this, you just told your TableViewController that it is responsible for the implementation of the DetailViewController's delegate
}
#pragma mark- DetailViewController's Delegate method
- (void)additem:(NSString *)Name MOBILE:(NSString *)Mobile
{
self.contactName=Name;
self.contactNo=Mobile;
[self.contactNameArray addObject:self.contactName]; //added the new entry
[self.contactMobileNoArray addObject:self.contactNo]; //added the new entry
[self.tableView reloadData]; //reload the table right after you updated the arrays
}
#end
This should help you with all your queries. If there is a change in the ContactTableViewController.m file, I added one or more comments. I tried to run the app and this is working properly.
Hey Just add this line in your view did load method of Contacttableviewcontroller.
DetailViewController *detailVc=[DetailViewController alloc]init];
detailVc.delegate =self;
Try this one
detailviewcontrollerdelegate
#import <Foundation/Foundation.h>
#protocol detailviewcontrollerdelegate<NSObject>
- (void)additem:(NSString *)Name MOBILE:(NSString *)Mobile;
#end
Detailviewcontroller.h
#import <UIKit/UIKit.h>
#import "detailviewcontrollerdelegate.h"
#interface DetaiViewController : UIViewController{
id< detailviewcontrollerdelegate > delegate;
}
#property (nonatomic, assign) id< detailviewcontrollerdelegate > delegate;
#property (weak, nonatomic) IBOutlet UITextField *nametextfield;
#property (weak, nonatomic) IBOutlet UITextField *mobiletextfield;
- (IBAction)Save:(id)sender;
and other as u have done make it same
**Detailviewcontroller.m**
- (IBAction)Save:(id)sender {
[self.delegate additem:self.nametextfield.text MOBILE:self.mobiletextfield.text];
}

Unable to call method from one class to another class while using ARC

I know how to call a method of one class to another class. However This time its not working for me and its just driving me nuts. Below is my code
MenuPageCell.h
#import <UIKit/UIKit.h>
#class MenuPageViewController;
#interface MenuPageCell : UITableViewCell{
NSInteger m_cellIndex;
MenuPageViewController *m_parentViewController;
}
#property(nonatomic, assign) NSInteger m_cellIndex;
#property(nonatomic, strong) MenuPageViewController *m_parentViewController;
-(IBAction) addToCart;
#end
MenuPAgeCell.m
#import "MenuPageCell.h"
#import "MenuPageViewController.h"
#implementation MenuPageCell
#synthesize m_cellIndex;
#synthesize m_parentViewController;
- (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
{
self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
if (self) {
// Initialization code
}
return self;
}
-(IBAction) addToCart
{
NSLog(#"Add To cart = %d",self.m_cellIndex);
[m_parentViewController addItemToCart:self.m_cellIndex];
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated
{
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
MenuPageViewController.m
-(void) addItemToCart:(NSInteger)aIndexItem
{
NSLog(#"In Add to Cart method");
}
Now, This code works fine for non ARC Used project but its not working for me. I know it should be silly mistake but I'm unable to figure it out.
Thanks & regards
Mayur
Referencing ViewController from a cell is a design flaw, consider using delegate instead. But if you really need the ViewController property, make it weak instead of strong because currently you end up with retain cycle.
#protocol MenuPageCellDelegate<NSObject>
- (void)addItemToCart:(NSInteger)aIndexItem;
#end
#interface MenuPageCell : UITableViewCell {
NSInteger m_cellIndex;
}
#property(nonatomic, assign) NSInteger m_cellIndex;
#property(nonatomic, weak) id<MenuPageCellDelegate> delegate;
-(IBAction) addToCart;
#end
#implementation MenuPageCell
...
-(IBAction) addToCart
{
NSLog(#"Add To cart = %d",self.m_cellIndex);
if ([self.delegate responsToSelector:#selector(addItemToCart:)]) {
[self.delegate addItemToCart:self.m_cellIndex];
}
}
...
#end
Add MenuPageCellDelegate to the list of implemented protocols of MenuPageViewController and (if it's implementing UITableViewDataSource protocol) in the tableView:cellForRowAtIndexPath: method write cell.delegate = self; instead of cell.m_parentViewController = self;
initialize your m_parentViewController in viewDidLoad method.
such like
m_parentViewController = [[yourViewControllerName alloc] init];
and then call
[m_parentViewController addItemToCart:self.m_cellIndex];
in the cellforrow method of your tableview add a selector to the cell button and also set the tag equal to the indexpath. now in the selector just distinguish between the different cells with the help of sender.tag.

Passing information between viewControllers in Storyboard

I am learning how to use storyboards by making a very simple app. On the main view controller (InfoViewController), I have a textField by the name: nameField. After entering text in this field, when I enter the save button, the text should should get appended to the array (list) (declared in TableViewController) and be displayed on the table in TableViewController.
Also, the segue identifier is: GoToTableViewController.
However, the text does not get passed from nameField to the list (array). At first, I assumed that I was making some mistake with the textField. So I replaced it with a static text. But that did not help either. Then I checked if the string has been added to the array by using NSLog() , but every time I get Null. From my understanding, the list (array) is not created until TableViewController is loaded. For that reason, I alloc and init list in InfoViewController. But it does not help.
Can somebody please help me find out the mistake that I am making?
Thanks!
Relevant sections of my code are as follows:
InfoViewController.h
#import <UIKit/UIKit.h>
#class TableViewController;
#interface InfoViewController : UIViewController
#property (weak, nonatomic) IBOutlet UITextField *nameField;
#property (strong, nonatomic) TableViewController *tableViewController;
#end
InfoViewController.m
#import "InfoViewController.h"
#import "TableViewController.h"
#implementation InfoViewController
#synthesize nameField;
#synthesize tableViewController;
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
tableViewController = [[TableViewController alloc] init];
tableViewController.list = [[NSMutableArray alloc] init];
}
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if([segue.identifier isEqual:#"GoToTableViewController"])
{
/* Pass data to list and then reloadTable data */
tableViewController = segue.destinationViewController;
tableViewController.infoViewController = self;
// (*) [tableViewController.list addObject:nameField.text];
// (*) [tableViewController.list addObject:#"Hi!"];
[tableViewController.list insertObject:#"Hi" atIndex:0];
// (**) NSLog(#"%#", [tableViewController.list objectAtIndex:0]);
[tableViewController.tableView reloadData];
}
}
#end
( * ) I inserted these statements to see if I was making a mistake with using the value in nameField.
( ** ) This statement is meant to check the value inserted in the array.
TableViewController.h
#import <UIKit/UIKit.h>
#class InfoViewController;
#interface TableViewController : UITableViewController
#property (nonatomic, strong) NSMutableArray *list;
#property (strong, nonatomic) InfoViewController *infoViewController;
#end
TableViewController.m
#import "TableViewController.h"
#import "InfoViewController.h"
#implementation TableViewController
#synthesize list;
#synthesize infoViewController;
- (void)viewDidLoad
{
[super viewDidLoad];
self.navigationItem.rightBarButtonItem = self.editButtonItem;
list = [[NSMutableArray alloc] init];
}
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{ return 1; }
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{ return list.count; }
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
cell.textLabel.text = [list objectAtIndex:indexPath.row];
return cell;
}
#end
Reload the table in viewWillAppear method of tableViewController:
[tableViewController.tableView reloadData];

NSInvalidArgumentException error occurs when calling setDelegate

I am trying to segue to another screen from a uitableview in iOS5. I have set up a delegate etc. which seems to work (the segue occurs) but I think I need to "set delegate to initialize the data I want to display in the new screen. I get a NSInvalidArgumentException error though when I call it is prepareforsegue.
Here is the code for the uitableview part...
#import "iTanksV2ListViewController.h"
#import "tank.h"
#import "tankDetailViewController.h"
#interface iTanksV2ListViewController ()
#property tank *selectedTank;
#end
#implementation iTanksV2ListViewController
#synthesize tanks = _tanks;
#synthesize tankTableView = _tankTableView;
#synthesize delegate = _delegate;
#synthesize selectedTank = _selectedTank;
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
self.tankTableView.delegate = self;
self.tankTableView.dataSource = self;
}
-(void) prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if([segue.identifier isEqualToString:#"Show Tank Details"])
{
UILabel *myLabel = [[UILabel alloc] init];
myLabel.text = self.selectedTank.tankNumber;
[segue.destinationViewController setTankNumberLabel:myLabel];
[segue.destinationViewController setDelegate:self]; ///this is where it fails!!!
}
}
#pragma mark - Table view delegate
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
self.selectedTank = [self.tanks objectAtIndex:indexPath.row];
[self.delegate iTanksListViewController:self choseTank:self.selectedTank];
}
and then in the detail view I use the following...
-(void)iTanksListViewController:(iTanksV2ListViewController *)sender choseTank:(id)tank
{
self.tankToShow = tank;
}
but this doesn't get called - presumably because i don't successfully call the setdelegate method?!
You must not have synthesized your delegate property. Also, make sure that your header file properly has the delegate protocol referenced like
#interface TankDetailViewController : UITableViewController <DELEGATEPROTOCOL>
I thought I had... this snippet is from the itanksv2listviewcontroller header:
#interface iTanksV2ListViewController : UITableViewController
#property (nonatomic, strong) NSArray *tanks;
#property (weak, nonatomic) IBOutlet UITableView *tankTableView;
#property (weak, nonatomic) id <iTanksV2ListViewControllerDelegate> delegate;
#end
and this from the m file :
#synthesize delegate = _delegate;
and this is what I have put in the detailview m file:
#interface tankDetailViewController () <iTanksV2ListViewControllerDelegate>
#end

Resources