how to force view to rotate to landscape in viewdidload? - ios5

Hi I'm using following code to show my app's login screen.
LoginViewController * loginController = [[LoginViewController alloc] initWithNibName:#"LoginViewController" bundle:nil];
UINavigationController * navController = [[UINavigationController alloc] initWithRootViewController:loginController];
navController.modalPresentationStyle = UIModalPresentationFormSheet;
[self.navigationController presentModalViewController:navController animated:YES];
Its loading properly. Here my problem is my app should be in landscape mode only. Here I'm using UIModalPresentationFormSheet so app is automatically appearing in portrait mode. I would like to force my app to change to landscape mode after this login view loads. some one please help me how to rotate my view into landscape mode after this UIModalPresentationFormSheet loads. (It means in LoginViewController's viewDidLoad mode I have to force my app to change to landscape mode. How can I achieve that). Thanks in advance

Try re-writing your User Interface Frame attributes with landscape co-ordinate values.
Do this in
- (void)willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation
duration:(NSTimeInterval)duration
and with the proviso
[super willAnimateRotationToInterfaceOrientation:toInterfaceOrientation duration:duration];
if (toInterfaceOrientation == UIInterfaceOrientationLandscapeLeft
|| toInterfaceOrientation == UIInterfaceOrientationLandscapeRight)

Related

launch orientation of iPad is incorrect for landscape orientation (upside down)

I read a few different posts on the orientation on launch, but I'm still unsure how it works. We are only supporting landscape orientation. In didFinishLaunchingWithOptions, I do:
HomeController *myHome = [[HomeController alloc] initWithNibName:#"HomeController" bundle:nil];
myHome.navigationItem.title = #"Your Dashboard";
UINavigationController *navController = [[UINavigationController alloc] initWithRootViewController:myHome];
[myHome release];
self.navigationController = navController;
[navController release];
self.window.rootViewController = self.navigationController;
In my HomeController class:
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return UIInterfaceOrientationIsLandscape(interfaceOrientation);
}
When I start the app however on the device, it can start upside down. How do I avoid that from happening? I saw some posts on people detecting for the status bar orientation in didFinishLaunchingWithOptions. If I do this after the self.window.rootViewController = self.navigationController; code:
NSLog(#"%i", [UIApplication sharedApplication].statusBarOrientation);
I always get 3. From there, I'm not sure what I can do to fix the upside down issue. Thanks.
I think you need to specify the supported orientations in your Info.plist. See the Supported interface configurations and Supported interface configurations (iPad) in your Info.plist.

Presenting ModalViewController turns the orientation of my app on start up

I'm trying to only support landscape. There's a new requirement to show this dialog box that explains some things about our app the first time. So in my first view controller that gets launched, in viewDidLoad, I have this code:
BOOL showFirstTimeUse = [[NSUserDefaults standardUserDefaults] boolForKey:#"ShowFirstTimeUse"];
if (!showFirstTimeUse) {
FirstUseViewController *tvc = [[FirstUseViewController alloc] initWithNibName:#"FirstUseViewController" bundle:nil];
tvc.modalPresentationStyle = UIModalPresentationFormSheet;
tvc.modalTransitionStyle = UIModalTransitionStyleFlipHorizontal;
[self presentModalViewController:tvc animated:YES];
[tvc release];
}
Then in the FirstUseViewController, I have this defined:
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
// Return YES for supported orientations
return UIInterfaceOrientationLandscapeLeft | UIInterfaceOrientationLandscapeRight;
}
In IB, I have not changed any of the default settings. I basically just dropped a UIWebView to the upper left hand side of the screen to show my data and connected an outlet to it so I can show formatted text easily.
When I run my app now, the presentation of this view controller causes my app to start in portrait rather than landscape. How do I fix this? Thanks.
Your implementation of shouldAutorotateToInterfaceOrientation: is faulty; It will always evaluate true. You likely want to use:
return UIInterfaceOrientationIsLandscape(interfaceOrientation);

UIImagePicker Shows blank when application in landscape

I am using navigation based application here when i call UIImagePicker then it show blank when the screen is in landscape but this shows correctly when the screen in portrait.
How can i change screen to portrait when its in landscape.
I using the code to call photo album is
UIImagePickerController *picker = [[UIImagePickerController alloc] init];
picker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
picker.delegate = self;
[self presentModalViewController:picker animated:YES];
[picker release];
Edited:
Actually i am using TabBarController Which was pushed from another view using the concept of navigationController then when i tried to call UIImagePickerController when it is in landscape then shows blank.
But without TabBarController UIImagePickerController works perfect(Automatically rotate to portrait)..
So how could i call UIImagePickerController when in landscape in TabBarController.
Thanks..
If this happens in a UIViewController then do the following so that the view is never rotated:
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return NO;
}
if u want to forcefully rotate in portrait use
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return (interfaceOrientation==UIInterfaceOrientationPortrait||UIInterfaceOrientationPortraitUpsideDown)
}
UIImagePickerController is portrait-only, see the documentation:
Important: The UIImagePickerController class supports portrait
mode only. This class is intended to be used as-is and does not
support subclassing. The view hierarchy for this class is private and
must not be modified [...]

UIViewController landscape mode buttons not working

I'm trying to get an app working in landscape mode which I've very nearly done, but for some reason the buttons on my view aren't working (ie. they don't press). I'm using a root view controller which loads the initial view controller as follows :
- (void)viewDidLoad
{
[super viewDidLoad];
StartViewController *viewController = [[StartViewController alloc] initWithNibName:#"StartView" bundle:nil];
self.startViewController = viewController;
startViewController.delegate = self;
[viewController release];
[self.view addSubview:startViewController.view];
}
I've also set the Initial Interface Orientation value in my Info.plist file and overridden the following in my root view controller :
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
// Return YES for supported orientations
return((interfaceOrientation == UIInterfaceOrientationLandscapeRight) ||
(interfaceOrientation == UIInterfaceOrientationLandscapeLeft));
//return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
The view loads fine and fills the screen in landscape mode as it should, but for some reason I just can't press any of the buttons on the view.
I'm sure it's something simple related to me using a root view controller because I've managed to get this to work fine before with an app with just a single view controller.
Can anybody help me out here?
I think the problem is somewhere in xib.
E.g. the button is placed on UIView with incorrect resize masks. So that in landscape mode the button appears outside the view, and touches can't reach the button. You can check it setting clipSubviews in all the parent view -- if I'm right, you will not see the button any more.
I had a simular problem. In my case I was subclassing a UITableViewCell and I has overwritten the layoutSubviews method. In there I was doing translations. But I forgot to put the [super layoutSubviews]; before my implementation. After I put it htere, the button were working again in landscape mode. It was strange that in portrait it worked and in landscape not.

20px gap on top of landscape view in iPhone app running on iPad

I am running an "iPhone-only" app in the iPad simulator...When the orientation of the device is changed to landscape mode, I have a view controller that kicks in and programmatically loads a WebView. This works swimmingly in the iPhone (no gap on top of landscape view), but when simulating in the iPad, there's a 20px (I think?) gap at the top of the view.
Here's the code in the landscape view controller's viewDidLoad where I load the WebView:
[super viewDidLoad];
// Initialize webview and add as a subview to LandscapeController's view
CGRect webFrame = [[UIScreen mainScreen] bounds]; // Use bounds to take up entire screen
self.myWebView = [[[UIWebView alloc] initWithFrame:webFrame] autorelease];
self.myWebView.scalesPageToFit = YES;
self.myWebView.autoresizingMask = (UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight);
self.myWebView.delegate = self;
[self.view addSubview: self.myWebView];
// remove status bar from top of screen
[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleBlackOpaque];
Setting the status bar to default, has no influence.
I can't seem to figure out why this would be fine on the iPhone, but emerge on the iPad???
Any ideas? Thanks in advance!
The screen bounds are in screen coordinates. You're adding the webview as a subview of self.view; its frame is in self.view coordinates. You want to fill your view, not the screen (your view is automatically resized by UIViewController/the rest of UIKit, which should end up resizing the web view to to auto-resizing):
self.myWebView = [[[UIWebView alloc] initWithFrame:self.view.bounds] autorelease];
It's not safe to change the status bar in -viewDidLoad. View-loading can happen anywhere (it happens when anything calls viewController.view). I'm also not sure why you're setting the style; you want to set hidden-ness:
In -viewWillAppear:, do [application setStatusBarHidden:YES animated:animated];
In -viewWillDisappear:, do [application setStatusBarHidden:NO animated:animated];
Finally, you might be seeing different behaviour because the iPad is running OS 3.2.x and the phone is running 3.1.x or 4.x. Additionally, the iPhone-compatibility mode uses a dummy status bar; the "real" status bar always stays at the edges of the screen.
20 pixels at the top is almost always invariably related to the height of the status bar.
The code you posted looks fine... for setting up the UIWebView. But you're adding it as a subview to your view controller's view. How is that sized? What is its frame?
I finally figured this out. The key missing component, which I didn't mention in the original post, is that the view controller that manages landscape is actually implemented as a modal view. (See the View Controller User Guide for code on how to do this) In concept, I have a Portrait view controller. (which is the primary controller) In the Portrait view controller's viewDidLoad I apply for a Notifier that is triggered off of a change in the orientation like so:
- (void)viewDidLoad {
[super viewDidLoad];
// SECTION to setup automatic alternate landscape view on rotation
// Uses a delegate to bring the landscape view controller up as a modal view controller
isShowingLandscapeView = NO;
// Create Landscape Controller programmatically
self.landscapeViewController = [[LandscapeViewController alloc] initWithNibName:#"LandscapeViewController" bundle:[NSBundle mainBundle]];
[[UIDevice currentDevice] beginGeneratingDeviceOrientationNotifications];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:#selector(orientationChanged:)
name:UIDeviceOrientationDidChangeNotification
object:nil];
// END SECTION landscape modal view controller
Then, when orientation changes this method is called:
- (void)orientationChanged:(NSNotification *)notification
{
UIDeviceOrientation deviceOrientation = [UIDevice currentDevice].orientation;
if (UIDeviceOrientationIsLandscape(deviceOrientation) && !isShowingLandscapeView)
{
// Load Landscape view
landscapeViewController.modalTransitionStyle = UIModalTransitionStyleCrossDissolve;
[self presentModalViewController:self.landscapeViewController animated:YES];
isShowingLandscapeView = YES;
}
At the same time I was removing the status bar from the Landscape view controller's viewWillAppear method:
- (void)viewWillAppear:(BOOL)animated
{
// remove status bar from top of screen
[[UIApplication sharedApplication] setStatusBarHidden:YES animated:animated];
self.myWebView.delegate = self; // setup the delegate as the web view is shown
}
and this is where the problem is introduced. The Portrait view controller captures the screen dimensions, before transitioning to landscape as a Modal View. Then, viewWillAppear, in the Landscape view controller, removes the status bar.
So, the solution is to move the
[[UIApplication sharedApplication] setStatusBarHidden:YES animated:animated];
statement to the orientationChanged method in the Portrait view controller, BEFORE transitioning to the Landscape Modal View.
- (void)orientationChanged:(NSNotification *)notification
{
UIDeviceOrientation deviceOrientation = [UIDevice currentDevice].orientation;
if (UIDeviceOrientationIsLandscape(deviceOrientation) && !isShowingLandscapeView)
{
// remove status bar from top of screen
// NOTE: this must be declared BEFORE presenting the Modal View!!!! If it's not, the landscape view will
// contain an ugly white bar in place of the missing status bar at the top of the view.
[[UIApplication sharedApplication] setStatusBarHidden:YES];
// Load Landscape view
landscapeViewController.modalTransitionStyle = UIModalTransitionStyleCrossDissolve;
[self presentModalViewController:self.landscapeViewController animated:YES];
isShowingLandscapeView = YES;
}
Note, that as tc helpfully mentioned above, if you want the status bar to appear when orienting back to Portrait, then you need
[[UIApplication sharedApplication] setStatusBarHidden:NO animated:animated];
in the viewWillDisappear method in the Landscape view controller.