December 14 2011
Modal views in universal iOS apps
by Brian Dunagan
On the iPhone, it’s quite normal to have an app slide a sheet up to create something or change settings. But on the iPad, that same view should be displayed in a popover . In a universal app, the key is shared code and XIBs for both approaches.
The code below is all that I needed to have a Settings sheet appear correctly in both an iPhone and iPad app. I simply identify the device type and then either present a popover controller or a modal view controller, using the same XIB. Clean code. Consistent interface.
// Main View Controller
- ( IBAction ) showSheet :( id ) sender {
if ([[ UIDevice currentDevice ] userInterfaceIdiom ] == UIUserInterfaceIdiomPad ) {
// iPad
if ( ! self . popoverController . popoverVisible ) {
self . popoverController = [[[ UIPopoverController alloc ] initWithContentViewController : self . myNavigationController ] autorelease ];
self . popoverController . popoverContentSize = CGSizeMake ( 400 , 400 );
self . popoverController . contentViewController . contentSizeForViewInPopover = CGSizeMake ( 400 , 400 );
self . popoverController . delegate = self ;
// Present the popover from the bar button.
[ self . popoverController presentPopoverFromBarButtonItem : self . navigationItem . rightBarButtonItem permittedArrowDirections : UIPopoverArrowDirectionAny animated : YES ];
}
}
else {
// iPhone
[ self . navigationController presentModalViewController : self . myNavigationController animated : YES ];
}
}
- ( void ) popoverControllerDidDismissPopover :( UIPopoverController * ) aPopoverController {
[ self . popoverController dismissPopoverAnimated : YES ];
}
- ( MyNavigationController * ) myNavigationController {
if ( myNavigationController == nil ) {
self . myNavigationController = [[ UINavigationController alloc ] initWithRootViewController : self . mySheetController ] autorelease ];
}
return myNavigationController ;
}
- ( MySheetController * ) mySheetController {
if ( mySheetController == nil ) {
self . mySheetController = [[ MySheetController alloc ] initWithNibName : @"MySheetView" bundle : nil ] autorelease ];
}
return mySheetController ;
}
// Sheet View Controller
- ( void ) viewWillAppear :( BOOL ) animated {
self . contentSizeForViewInPopover = CGMakeSize ( 400 , 400 );
[ super viewWillAppear : animated ];
}