In your view controller, override shouldAutorotateToInterfaceOrientation: declare your supported interface orientations. This property will / should be checked by the controller infrastructure every time the device orientation changes.
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)orientation { return (orientation == UIInterfaceOrientationLandscapeRight); }
This is the absolute minimum that your controller must fulfill. If you want to run the application in landscape mode, you need to add the following file to the .plist file:
<key>UIInterfaceOrientation</key> <string>UIInterfaceOrientationLandscapeRight</string>
Apple recommends that you only run landscape applications in Landscape mode (see HIG under User Guides> Start Instantly.
What's not in the documentation:
A bit of background:
Each time you try to load a different view controller other than the one loaded from the main nib, your view controller does not examine its supported interface orientations and does not set its frame. Only the first view controller associated with the window will be correctly installed.
Other people have suggested using a "MasterViewController" connected to the main window, to which other controllers add their subview views instead of connecting directly to the window. Although I found that this solution is a viable option, it does not work correctly in the case of modal view controllers added to these specified areas. There is also a problem if you have some subitems that should be able to autorotate (which will prevent the main controller).
Using an undocumented API to force orientation of an interface is also not an option.
Decision:
The best solution I have found so far is a modification of the "MasterViewController" workaround. Instead of using the custom "MasterViewController", a UINavigationController with a hidden navigation bar and a hidden tab bar is used. If all other views are popped / pulled out of the navigation stack of this controller, the control of the controller rotations in this stack will be correctly executed.
Modal controllers presented via presentModalViewController:animated: from any of the view controllers in the UINavigationController navigation stack will be rotated and displayed with the correct layout. If you want your modal view controller to rotate in a different orientation than the parent view controller, you need to return the desired orientation from the shouldAutorotateToInterfaceOrientation method of the shouldAutorotateToInterfaceOrientation controller, while the modal view is Presented. In order to correctly restore the orientation of the interface when the modal controller is disabled, you must ensure that shouldAutorotateToInterfaceOrientation returns the desired orientation of the parent controller before calling dismissModalViewController:animated: To control this (e.g. BOOL isModalMailControllerActive_ ), you can use the private BOOL on your view controller.
Soon I will add part of the sample code. This is only the end. Please let me know if there are any unresolved issues or if something is not clear in this post. Feel free to edit and improve.