0

I have a view which is presented as full screen. I want the presented full screen view to be restricted just to portrait.

Can anyone help me out with restricting only one view as portrait? It should not turn to landscape.

user3202087
  • 149
  • 12
  • It is a separate view controller or just a UIView? – Liftoff Feb 14 '14 at 05:01
  • separate viewController. Alltogether i have two viewControllers.For the second one i want to restrict to portrait. – user3202087 Feb 14 '14 at 05:04
  • SEE: http://stackoverflow.com/questions/18595561/alternative-ios-layouts-for-portrait-and-landscape-using-just-one-xib-file – Velmurugan S Feb 14 '14 at 05:36
  • It did not help me :( Can you post a code here which i have to do programmatically and not using xib. – user3202087 Feb 14 '14 at 05:54
  • possible duplicate of [Do "Supported Interface Orientations" have precedent?](http://stackoverflow.com/questions/16376237/do-supported-interface-orientations-have-precedent) – matt Feb 28 '14 at 03:03
  • I agree my question must have been a duplication but i wasn't getting out the exact solution with the other related post, that is the reason i posted a new question just to clear my doubt. – user3202087 Mar 02 '14 at 12:36

2 Answers2

2

The code you use depends on the iOS you are targeting:

iOS 6+

There's a method called supportedInterfaceOrientations that does what you are looking for:

- (NSUInteger)supportedInterfaceOrientations
{
    //If you want to support landscape
    return UIInterfaceOrientationMaskAll;
    
    //If you don't
    return UIInterfaceOrientationMaskPortrait;
}

 - (BOOL)shouldAutorotate {
    return YES;
}

Put the according return statement in each view controller.


iOS 5 and prior:

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation {
    return !(UIInterfaceOrientationIsLandscape(toInterfaceOrientation));
}
Community
  • 1
  • 1
Liftoff
  • 24,717
  • 13
  • 66
  • 119
  • Yes. Thankyou it worked on my simulator. I will build it on iPad and check and give you the feedback. – user3202087 Feb 14 '14 at 05:22
  • Hey it is not working in my main app wherein there are many viewControllers presented. And in the one i wanted to restrict to portrait there i added the above code but its not working. Its showing in landscape also. Any other way you have? – user3202087 Feb 14 '14 at 05:26
  • What iOS version are you writing this for? – Liftoff Feb 14 '14 at 05:28
  • Check my edit. I forgot to include the autorotate method, and I added the code for iOS 5- – Liftoff Feb 14 '14 at 05:34
  • I am using this for iOS 6 and above. – user3202087 Feb 14 '14 at 06:15
  • :Hey yes this worked for presenting view controllers. Thanx a lot. :) – user3202087 Feb 14 '14 at 07:24
  • What does the sshouldAutorotate property do? Can you tell me? Does it handle the portrait and portraitUpsideDown both? – user3202087 Feb 14 '14 at 07:42
  • @user3202087 shouldAutorotate was a new thing introduced in iOS 6 to handle when the application should check available rotations. Basically by putting that in there you are telling the ViewController to check it's supported rotation orientations when the device is rotated, rather than inheriting it's supported rotations from the parent view controller. – Liftoff Feb 14 '14 at 08:34
  • but the code is working just for portrait and not for portaraitUpsideDown and if i put in the code return return UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationPortraitUpsideDown, it gives me error. Can you tell me why? – user3202087 Feb 14 '14 at 09:05
  • In the supported orientations method, you have to use Masking: `(UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationMaskPortraitUpsideDown)` – Liftoff Feb 14 '14 at 09:07
1

If you are using the model presenting between VCs, @David 's answer is correct. However if you are using UINavigationController push/pop, things will be more complicated.

- (NSUInteger)supportedInterfaceOrientations and - (BOOL)shouldAutorotate only be called after device rotated or root controller changed. push/pop will not make it.


In iOS5 and prior, there is an API:

[[UIDevice currentDevice] setOrientation: UIInterfaceOrientationPortrait];

But it was deprecated. Apple make it private.

You still can use objc runtime api to call it in iOS 6+, such as:

objc_msgSend([UIDevice currentDevice], @selector(setOrientation:), @(UIInterfaceOrientationPortrait));

or

[[UIDevice currentDevice] setValue:@(UIInterfaceOrientationPortrait)
                            forKey:@"orientation"];

NOTE: it's private API, This may be rejected by the App Store.


Another tricky way is that, just present a empty VC then dismiss it in viewDidAppear, something like:

[self presentViewController:[UIViewController new]
              animated:NO
              completion:^{
                  [self dismissViewControllerAnimated:NO completion:nil];
              }];

This will make the - (NSUInteger)supportedInterfaceOrientations and - (BOOL)shouldAutorotate to be called.


If you are not satisfied with those above. Try to make your own NavigationController, or check out this Question: Why can't I force landscape orientation when use UINavigationController?.

Community
  • 1
  • 1
lancy
  • 857
  • 6
  • 22
  • Thanx it works well. But there is one problem when that view opens it becomes portrait but when i rotate it to left 4 times, the 4th time it came into landscape. :( – user3202087 Feb 14 '14 at 06:55
  • @user3202087 I couldn't figure out why for now with your description, maybe you could ask a new question and post the code. – lancy Feb 14 '14 at 07:03
  • Actually, i was using navigationController push/pop so thats why David's code was not working and your code had an issue(the one mentioned above) but i changed the push/pop to presenting viewController. Anyway Thanx for the help you ppl gave. :) – user3202087 Feb 14 '14 at 07:27
  • 1
    This is definitely wrong. If you're trying to force a particular interface orientation you want to call `[UIApplication sharedApplication].statusBarOrientation = UIInterfaceOrientationPortrait;` Apple has provided two different enums that are similar, but very different: UIDeviceOrientation and UIInterfaceOrientation. The device property is read-only, because you can't force the physical device to change orientation! The statusBarOrientation *is* writable, and will do what you were trying to do with setValue:forKey: – Dan Jackson Jun 11 '15 at 19:10