Reputation: 12490
When doing a modal segue, does the originating ViewController get discarded after the segue is performed? I am setting the destination controller's delegate to the source ViewController, but when the destination ViewController.viewDidLoad, the self.delegate is nil...
The following code will produce the log message "ListViewController.viewDidLoad: My delegate is nil :("
[Source] MapViewController:
- (void) prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
if([segue.identifier isEqualToString:@"mapToList"]){
NSLog(@"MapViewController.prepareForSegue: Segue mapToList being called, setting LisViewController's delegate to myself");
[segue.destinationViewController setDelegate:self];
if(!self){
NSLog(@"MapViewController.prepareForSegue: I am nil.");
} else {
NSLog(@"MapViewController.prepareForSegue: I am NOT nil.");
}
}
}
[Destination] ListViewController:
- (void)viewDidLoad
{
[super viewDidLoad];
if(!self.delegate){
NSLog(@"ListViewController.viewDidLoad: My delegate is nil :(");
} else {
NSLog(@"ListViewController.viewDidLoad: My delegate populated");
}
}
Upvotes: 2
Views: 2658
Reputation: 393
This is an old question but I came upon it when running into the same issue myself. Couple of things here:
So the fix is in your prepareForSeque:
UINavigationController *navController = segue.destinationViewController;
MyRealDestViewController *myRealDestViewController = (MyRealDestViewController)navController.topViewController;
myRealDestViewController.delegate = self;
Upvotes: 3
Reputation: 1359
If the segue is to a NavigationController
then the destinationViewController
loses the delegate.
I got around this problem by having the modal segue into the destinationViewController
, and then adding NavigationBar
and Bar Buttons
to simulate the navigation controller (I assume you wrapped the destinationViewController
in a NavigationController
for the "done" and "cancel" buttons).
Set the delegate as normal in the rootViewController
:
-(void) prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
if ([segue.identifier isEqualToString:@"segueToModalView"]){
[segue.destinationViewController setDelegate:self];
}
}
Hope that helps
Upvotes: 1
Reputation: 4111
Your code seems correct, the only thing I have done differently is test this in a skeleton framework I have that is a tableviewcontroller nested in a navigationcontroller. I just tested with the following code and it works fine for me:
RootViewController .h:
@interface RootTableViewController : UITableViewController <newTest>
Prepare for Segue (in rootViewController):
-(void) prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
if ([segue.identifier isEqualToString:@"segueToModalView"]){
[segue.destinationViewController setDelegate:self];
}
}
Top of Modal View Controller .h:
@protocol newTest <NSObject>
-(void) hello;
@end
Property Declaration in Modal View:
@property (nonatomic, strong) id <newTest> delegate;
ViewDidLoad in Modal View:
- (void)viewDidLoad
{
[super viewDidLoad];
NSLog(@"%@", self.delegate);
}
My NSLog of self.delegate properly prints out and my code appears to be more or less the same as yours. Is your property declared correctly?
Upvotes: 3