NickHowes
NickHowes

Reputation: 143

Switching between modal view controllers

My app allows the user to switch between two different modal view controllers (for two different styles of data entry). The code below used to work (in iOS 4.3 and earlier):

    UIViewController * parent = current.parentViewController;
    [current dismissModalViewControllerAnimated:NO];
    svc.modalPresentationStyle = UIModalPresentationFormSheet;
    [parent presentModalViewController:svc animated:NO];
    [svc release];

but no longer (in iOS 5) - the "current" view controller dismisses, but "svc" is not presented.

Any idea why it broke (i.e. what did I do wrong)? Any idea how to do it "right" (so that it works on 5.0 as well as 4.3 and earlier)?

Upvotes: 1

Views: 5016

Answers (1)

v1Axvw
v1Axvw

Reputation: 3054

Jeff Hay was totally right in his comment except for one thing. You should do it in the -viewDidAppear: method of the view controller which originally presented the first modal view controller.

Example:

// MyViewController.h
@interface MyViewController : UIViewController {
    BOOL _shouldPresentSecondModalViewController;
}
@end

// MyViewController.m
@implementation MyViewController
- (void)viewDidAppear:(BOOL)animated {
    if(_shouldPresentSecondModalViewController) {
        UINavigationController *myNavCon;
        // Code to create second modal navigation controller
        [self presentModalViewController:myNavCon animated:YES];
        _shouldPresentSecondModalViewController = NO;
    }
}

- (void)presentFirstViewController {
    UINavigationController *myNavCon;
    // Code to create the first navigation controller
    _shouldPresentSecondModalViewController = YES;
    [self presentModalViewController:myNavCon animated:YES];
}
@end

EDIT:
Now, if you want to pass data between the two modal view controllers, you can use a delegate.

// FirstModalViewControllerDelegate.h
@protocol FirstModalViewControllerDelegate
@optional
- (void)controller:(FirstModalViewControllerDelegate *)vc shouldShowData:(id)anyType;
@end

// MyViewController.h
@interface MyViewController : UIViewController <FirstModalViewControllerDelegate> {
    id _dataToDisplay;
}
@end

// MyViewController.m
@implementation MyViewController
- (void)viewDidAppear:(BOOL)animated {
    if(_dataToDisplay != nil) {
        UINavigationController *myNavCon;
        // Code to create second modal navigation controller
        [self presentModalViewController:myNavCon animated:YES];
        [_dataToDisplay release];
        _dataToDisplay = nil;
    }
}

- (void)presentFirstViewController {
    UINavigationController *myNavCon;
    FirstModalViewController *myCon;
    // Code to create the first modal view controller

    [myCon setDelegate:self];

    myNavCon = [[UINavigationController alloc] initWithRootViewController:myCon];

    [self presentModalViewController:myNavCon animated:YES];
    [myNavCon release];
}

- (void)controller:(FirstModalViewControllerDelegate *)vc shouldShowData:(id)anyType {
    /* This method will get called if the first modal view controller wants to display
    some data. If the first modal view controller doesn't call this method, the
    _dataToDisplay instance variable will stay nil. However, in that case, you'll of
    course need to implement other methods to, like a response to a Done button, dismiss
    the modal view controller */
    [self dismissModalViewController];
    _dataToDisplay = [anyType retain];
}
@end

Upvotes: 3

Related Questions