如何在iOS中处理不同的方向

补充 :你可以在github ios6rotations上访问这个项目


对不起,在iOS 6中提问有关屏幕旋转的问题,但这真的是一个痛苦的屁股..我仍然无法完全理解 – 由于某种原因,它在某些情况下行为不同。

我在testing应用程序中有以下简单的视图层次结构:

我试图达到的目的是 – 只将蓝色控制器保持在风景中,而红色控制器只能用于风景

我有这样的代码里面的UINavigationController的子类:

@implementation CustomNavController - (BOOL)shouldAutorotate { return [[self.viewControllers lastObject] shouldAutorotate]; } - (NSUInteger)supportedInterfaceOrientations { return [[self.viewControllers lastObject] supportedInterfaceOrientations]; } - (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation { return [[self.viewControllers lastObject] preferredInterfaceOrientationForPresentation]; } @end 

在我的蓝色控制器中我实现了这个:

 - (BOOL)shouldAutorotate { return YES; } - (NSUInteger)supportedInterfaceOrientations { return UIInterfaceOrientationMaskLandscape; } 

而在红色的控制器中:

 - (BOOL)shouldAutorotate { return YES; } - (NSUInteger)supportedInterfaceOrientations { return UIInterfaceOrientationMaskPortrait; } 

现在我有以下行为:

  1. 应用程序开始在横向(确定)
  2. 当我按下button时,我的红色控制器也被推入横向(这是不正确的,因为它必须以纵向显示)
  3. 它成功地旋转到肖像,而不是向后旋转到风景
  4. 如果我将红色控制器置于纵向模式,则我的蓝色控制器(限于横向模式)以纵向模式显示。

PS所有我的旋转方法(上面张贴)正在调用正常(顺便说一句,为什么这些方法调用了每个屏幕过渡很多次 – 5-6次)

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation不会被推送调用

所有(除了portraitUpsideDown)方向都包含在plist中。

问题是 – 如何强制旋转支持每个控制器的方向?

我build议你在这里(作为答案)发布任何100%的工作代码来处理ios6中的旋转(例如,如果你有一些与SplitController的iPad) – 我会保持这个问题在最喜欢的,当我需要在一个地方处理一些特定的情况。 干杯!

增加:请不要张贴这从风景对画象的答复我希望有更加优雅的方式做它。

使用-[UIDevice setOrientation:]是一个私人的API,并会让你的应用程序被拒绝。 看到这个问题 。

你问的是不可能使用公共API,也不build议从HIG的angular度来看。 什么是支持,你应该实现,是不同的视图控制器不同的支持接口方向的模态呈现。 这就是为什么UINavigationController的默认实现是始终旋转的; 它假定所有视图控制器都具有相同的支持的接口方向。

以iPhone上的video回放为例。 打开video应用程序(iOS附带)。 根视图控制器只支持纵向。 但是,启动一个video,popup一个只支持风景界面方向的模式视图控制器。 这看起来正是你想要达到的行为。

这就是为什么preferredInterfaceOrientationForPresentation没有被调用。 preferredInterfaceOrientationForPresentation仅在使用presentViewController:animated:时被调用presentViewController:animated:

一个小问题,如果在场景的每个阶段都需要导航栏,则需要用导航控制器将每个模态视图控制器放在一起。 然后,您可以在prepareForSegue:传递所需的数据prepareForSegue:通过访问topViewController中的导航控制器对象的topViewController。


这里是一个示例项目,根据您的要求正确运行(或至less会给你如何实现的想法):

http://www.mediafire.com/?zw3qesn8w4v66hy

我的两分钱。

您可以快速提交一个空的透明模态视图,然后closures它 ,也许在ViewDidLoad:或viewWillAppear:在您的ViewController和ViewControllerSecond类作为一个快速的解决方法。

另外,在故事板中,您可以将ViewController类的方向设置为可视化的横向

使用这条线以编程方式改变方向… 工作100%

 [[UIDevice currentDevice] setOrientation:UIInterfaceOrientationLandscapeRight]; 

并且当你在这个时候添加这行的时候会出现一个警告,为了除去这个警告,只需要在你的实现文件中添加下面的代码。

 @interface UIDevice (MyPrivateNameThatAppleWouldNeverUseGoesHere) - (void) setOrientation:(UIInterfaceOrientation)orientation; @end 

然后在波纹pipe法中,如果需要的话就写这个代码。

 - (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation { // Return your supported orientations if (currentMainView==blueOne) { return toInterfaceOrientation== UIInterfaceOrientationPortrait; } } 

我在我的一个应用程序中有类似的情况(虽然请注意,我没有使用UINavigationController)。

更改两个viewControllers中的shouldAutorotate方法:

 //in blue (landscape only) -(BOOL)shouldAutorotate{ if (UIInterfaceOrientationIsLandscape(self.interfaceOrientation)) { return YES; } else { return NO; } } //in red (portrait only) -(BOOL)shouldAutorotate{ if (self.interfaceOrientation == UIInterfaceOrientationPortrait) { //note that UIInterfaceOrientationIsPortrait(self.interfaceOrientation) will return yes for UIInterfaceOrientationPortraitUpsideDown return YES; } else { return NO; } } 

保持supportedInterfaceOrientations方法相同。

 #pragma mark- Orientation Delegate Method: - (void)willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration { Orientation = [UIApplication sharedApplication].statusBarOrientation; if (Orientation == UIInterfaceOrientationLandscapeLeft || Orientation == UIInterfaceOrientationLandscapeRight) { // self.scrollView.contentOffset = CGPointMake(self.view.bounds.size.width,1200); [scrollView setScrollEnabled:YES]; [scrollView setContentSize:CGSizeMake(768, 2150)]; }else if (Orientation == UIInterfaceOrientationPortrait || Orientation == UIInterfaceOrientationPortraitUpsideDown) { [scrollView setScrollEnabled:YES]; [scrollView setContentSize:CGSizeMake(768, 1750)]; } } 

为了一起使用定位导航,你应该像一个数组一样的视图控制器。

在结帐之后,

 -(BOOL)shouldAutorotate { return [[self.viewControllers lastObject] shouldAutorotate]; } -(NSUInteger)supportedInterfaceOrientations { return [[self.viewControllers lastObject] supportedInterfaceOrientations]; } - (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation { return [[self.viewControllers lastObject] preferredInterfaceOrientationForPresentation]; } 

这种方法的改变将会对你有所帮助。

享受编程!