Force first screen of ios application to be portrait but other screens landscape ios 6+ - ios

I used this code for forcing my Home screen (first screen of my application) be portrait while other screens remain supporting all orientations:
public class RltNavigationController : UINavigationController
{
public RltNavigationController () : base ()
{
}
public override UIInterfaceOrientationMask GetSupportedInterfaceOrientations ()
{
if(this.TopViewController is HomeScreen )
return UIInterfaceOrientationMask.Portrait ;
else
return UIInterfaceOrientationMask.AllButUpsideDown ;
}
public override bool ShouldAutorotateToInterfaceOrientation (UIInterfaceOrientation toInterfaceOrientation)
{
// Return true for supported orientations
if(this.TopViewController is HomeScreen )
return (toInterfaceOrientation == UIInterfaceOrientation.Portrait );
else
return (toInterfaceOrientation != UIInterfaceOrientation.PortraitUpsideDown) ;
}
}
Now, suppose that the device is on the landscape orientation at home screen (Device is lanscape but screen just show portrait). Now if user go to other views, other views now show portrait while it should show landscape. What solution I can choose in order to load second views with theirs actual rotation?
EDIT
Thanks for all answers, Just notice that already the problem is not that I can not force the screen to be portrait. For understanding the problem please follow the scenario:
-> First screen forced to be portrait.
-> Device is landscape right and I'm in home screen(so home screen show portrait)
-> Now I switch to another screen that support all orientation
-> at another screen because the parent screen was portrait it show portrait (while because device is landscape it should show landscape)

You can also directly select from the XIB a particular viewController be Landscape or Portrait and the same loads.

You can not explicitly say, viewController be landscape and the view will be landscape. The way it works is, you ask the controller that is controller the screen, this may be a navigation controller, tab view controller, a modal, how they want to be able to rotate. If you have a navigation controller then all viewController will only have the rotation of your navigation controller.
There were a few tricks like subclassing the navigation controller and over the should auto rotate method, call [self.visibleViewController shouldAutoRotate]; which works for making screens rotate and not rotate, but if you have only 1 screen that supports all orientations and all the others do not, then you have a pushing/popping error where if you push or pop while in that different orientation the next viewController will be in that orientation.
Since you can't directly tell the rootViewController to explicitly rotate, the next best solutions are,
A: Use QuartzCore to manually rotate the view yourself
B: have a separate xib file for each orientation so when you rotate to landscape you see the landscape viewController and vice versa

The easiest way to do this is to create a custom navigation controller (subclass of UINavigationController) that inherits its rotation based on the currently visible view controller
Inside your custom navigation controller:
-(NSUInteger) supportedInterfaceOrientations {
return UIInterfaceOrientationMaskAllButUpsideDown;
}
-(BOOL) shouldAutorotate {
return self.topViewController.shouldAutorotate;
}
Then inside any of the view controllers within that, add these methods:
-(BOOL)shouldAutorotate{
return NO;
}
-(NSUInteger)supportedInterfaceOrientations{
return UIInterfaceOrientationMaskPortrait;
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation{
return UIInterfaceOrientationPortrait;
}
That's for a view you DON'T want to autorotate. Modify that accordingly for views you do want to rotate.
Make sure your project settings have rotation in the orientations you want enabled, and make sure to use your custom navigation controller instead of the regular one for any view hierarchies that contain multiple possible rotations.
Note that you may run into problems if a view that is rotated is popped and the previous view is not rotatable. Off the top of my head, I'm not sure whether this will work properly.

Related

Landscape orientation for one view controller ios

I want to show one view controller in both orientation in iPhone. And when the screen is opening the preferred orientation should be portrait only. Then according to the device orientation it'll rotate. I found some solution and the screen is rotating too. But when I'm entering the screen it is auto rotating to landscape and than I've to manually rotate it to portrait.
Is there a simple solution to this problem?
You should implement preferredInterfaceOrientationForPresentation and
supportedInterfaceOrientations like:
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return UIDeviceOrientationPortrait;
}
//You don't actually need to implement this as UIInterfaceOrientationMaskAllButUpsideDown is the default for iPhone
- (UIInterfaceOrientationMask)supportedInterfaceOrientations
{
return UIInterfaceOrientationMaskAllButUpsideDown;
}

Auto-rotation for hidden view controllers(iOS7)

The app only supports landscape. First, I have a view controller. Inside it, I have a bottom bar view controller. When I click the bottom bar view controller, a settings view controller(modal view) appears. Then if I rotate 180 degrees, the settings view controller does rotate while the original view controller is upside down. Any ideas to fix it? This is only on iOS 7(not iOS 8).
In your settings view controller try this:
- (NSUInteger)supportedInterfaceOrientations {
return UIInterfaceOrientationMaskLandscape;
}
- (BOOL)shouldAutorotate {
return NO;
}
You can try also UIInterfaceOrientationMaskLandscapeLeft or UIInterfaceOrientationMaskLandscapeRight if you supports only one landscape orientation.

shouldAutorotate is not locking the screen orientation

I ma trying to lock screen orientation to only landscape orientation when a certain image is still visible, then when the image is hidden, unlock all orientations (targeting iOS 6):
-(BOOL)shouldAutorotate{
if (self.splashImageView.hidden == NO) {
return UIInterfaceOrientationMaskPortrait;//gets called when image is visible
}else{
return UIInterfaceOrientationMaskAll;//gets called when image is hidden
}
}
- (void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration {
[self shouldAutorotate];
}
As you may notice, shouldAutorotate is called properly but the screen is always supporting landscape orientation even when the image is still visible, is there something missing?
P.S: Please note I am trying to get that to work on a tabbar view controller (a UIViewController subclass).
In your appdelegate you have those two methods.but do you have setting like in your project settings -> go to summary tab and see if orientation is set to only landscape or all.Just try to set those.

Interface Orientation with TabBarController

I am using a Tab Bar Controller in my app. In the most part of the app's behavior we have one single orientation (interfaceOrientationPortrait). But i have a view that runs a video in WebView. When i am running this video, the orientation remains portrait. I want to put for all orientations.
Well, i used the return type YES in my Video's class. Nothing has changed. I changed the return type to YES in my RootViewController class. Nothing has changed.
I would like to change the orientation only for the Video.
View controllers that are part of a tab bar controller won't rotate to an orientation if any of the tab bar controllers can not rotate to that orientation (at least if the tab bar is visible). So maybe you want to update all your controllers' method in order to let the rotation happen if the web view controller is visible on the tab bar controller.
If you need a deeper explanation, just ask. Good luck!
Edit (example code)
This is what could be your rotation methods for your tab bar controller view controllers:
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
if ((self.tabBarController.selectedIndex == kMyWebViewControllerIndex))
{
return YES;
} else
{
return (orientation == UIInterfaceOrientationPortrait);
}
}
Is your web view in a view controller inside the tabBarController?
Try showing it in a modally presented view controller, it should work

Monotouch - View created in landscape orientation is displayed in portrait orientation

I've created a view controller and set the orientation of the view to Landscape in XCode 4.2 (Interface Builder). However, when I add the view, the view is displayed in Portrait orientation. I've overriden ShouldAutorotateToInterfaceOrientation in all view controllers to return true, and I've attempted to rotate the view manually using the following code:
this.View.Transform.Rotate (3.14f * .5f);
I have also tried to set the frame to a landscape frame (i.e. 480 X 320), though the frame of the view is already set correctly.
Just to clarify, the vast majority of my views are in Portrait. I would like to load the landscape view in a landscape orientation, irrespective of what orientation the device is actually in. Is this possible? If so, what am I missing?
Thanks in advance for any assistance on this matter!
UPDATE: I'm noticing that ShouldAutorotateToInterfaceOrientation is only called once when the view is loaded. It is not called when the device is rotated. Is this normal behavior?
ShouldAutorotateToInterfaceOrientation is called every time the device orientation changes.
public override bool ShouldAutorotateToInterfaceOrientation (UIInterfaceOrientation toInterfaceOrientation)
{
Console.Out.WriteLine(toInterfaceOrientation.ToString());
// Return true for supported orientations
// This particular screen is landscape only!
return (toInterfaceOrientation == UIInterfaceOrientation.LandscapeLeft || toInterfaceOrientation == UIInterfaceOrientation.LandscapeRight);
}
this code will only allow the view to orient itself in either landscapeleft or landscaperight mode, and writes the new device orientation to the console every time.
when you load the view, and push it onto (for instance) a UINavigationController however, it's still in portrait mode (and ShouldAutorotateToInterfaceOrientation is not called.)
From Objective-C, it's fairly easy to force a device orientation, but in MonoTouch, there appears to be no direct mapping.
the solution ;
Send a message to the objective-c runtime, specifying which orientation we want.
you can easily do this by adding the following to a view controller:
Selector orientationSetter;
private void SetOrientation (UIInterfaceOrientation toOrientation)
{
if (orientationSetter == null)
{
orientationSetter = new Selector ("setOrientation:");
}
Messaging.void_objc_msgSend_int (UIDevice.CurrentDevice.Handle,
orientationSetter.Handle, (int)toOrientation);
}
you can now manually change the orientation of the entire device.
What's more, is that if you use a UINavigationController, the orientation will return back to normal once this view is popped off the stack.
I think that for the Landscape view that you always want to display in Landscape Orientation, you need to return False within ShouldAutorotateToInterfaceOrientation or remove the override altogether. This will prevent the view from auto-rotating when the device is in portrait mode.

Resources