48

我一直在互联网上寻找解决方案,但一无所获。我正在尝试使我的 iOS 5 应用程序与 iOS 6 兼容。我无法让方向的东西正常工作。我无法检测到何时将发生轮换。这是我正在尝试的代码:

- (BOOL)shouldAutorotate {
    return NO;
}

- (NSUInteger)supportedInterfaceOrientations {
    return UIInterfaceOrientationMaskPortrait;
}
// pre-iOS 6 support
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation {
    return (toInterfaceOrientation == UIInterfaceOrientationPortrait);
}

新的 supportedInterfaceOrientation: 方法被调用得很好。但是, shouldAutorotate 方法不会触发。我需要在旋转时进行一些图像交换,但没有任何迹象表明旋转即将发生。

提前致谢。

4

9 回答 9

80

查看您的应用程序启动时是否收到以下错误。

应用程序窗口应该在应用程序启动结束时有一个根视图控制器

如果是这样,修复它的方法是在AppDelegate.m文件中进行以下更改(尽管似乎有很多答案如何解决这个问题):

// Replace
[self.window addSubview:[navigationController view]];  //OLD

// With
[self.window setRootViewController:navigationController];  //NEW

之后shouldAutoRotate应该正确调用。

于 2012-10-08T23:18:19.987 回答
45

当使用 UINavigationController 作为应用程序的基础时,我使用以下子类来灵活地允许最顶层的子视图控制器决定旋转。

@interface RotationAwareNavigationController : UINavigationController

@end

@implementation RotationAwareNavigationController

-(NSUInteger)supportedInterfaceOrientations {
    UIViewController *top = self.topViewController;
    return top.supportedInterfaceOrientations;
}

-(BOOL)shouldAutorotate {
    UIViewController *top = self.topViewController;
    return [top shouldAutorotate];
}

@end
于 2013-05-08T08:27:34.127 回答
15

该方法不是确定它的正确方法。正确的方法是willRotateToInterfaceOrientation:duration:

不推荐使用应该旋转到方向(与 shouldAutorotate 相对)方法,并且从 iOS 6 开始将不再调用它,但无论如何它并不意味着以您使用它的方式使用。

编辑对重复投票的回应。请解释为什么使用我指出的方法不是(引用 OP)“轮换即将发生的迹象”。问题的内容和标题不匹配。

于 2012-10-08T04:32:57.360 回答
10

看起来在 iOS 6 上,容器导航控制器在旋转时不会咨询子视图控制器:

iOS 6 发行说明中

现在,iOS 容器(例如 UINavigationController)不会咨询它们的子容器来确定它们是否应该自动旋转。默认情况下,应用程序和视图控制器支持的界面方向设置为 iPad 惯用语的 UIInterfaceOrientationMaskAll 和 iPhone 惯用语的 UIInterfaceOrientationMaskAllButUpsideDown 。

这种行为很容易测试。我所做的是使用相同的自定义视图控制器

  1. 第一种情况作为主视图控制器
  2. 第二种情况作为 UIPageViewController 的子项

在第一种情况下,自定义导航控制器中的所有内容都由与应用程序支持的方向相一致的shouldAutorotate组合supportedInterfaceOrientations决定supportedInterfaceOrientations

在第二种情况下,即使supportedInterfaceOrientationsUIPageViewController 调用了自定义视图控制器,也不会考虑返回值。如果这两个方法在 UIPageViewController 的子类中被覆盖,它就可以工作。我不确定它的副作用,因为这个类不应该是子类。

于 2012-10-26T08:20:33.773 回答
10

如果您viewController是 a 中的孩子viewControllerUINavigationController那么您可以执行以下操作:

  • 子类UINavigationController
  • shouldAutoRotate在你的子类中覆盖
  • 调用此方法时发送topViewController此消息

// 这个方法在你的UINavigationController子类里面

- (BOOL)shouldAutorotate
{
    if([self.topViewController respondsToSelector:@selector(shouldAutorotate)])
    {
        return [self.topViewController shouldAutorotate];
    }
    return NO;
}
  • 现在您的 viewController 将分别响应此方法。
  • 请注意,您可以对其他 orinetaion-methods 执行相同操作
于 2014-01-12T15:40:09.727 回答
1

当您的应用程序启动时,我也收到以下错误。

“应用程序窗口应该在应用程序启动结束时有一个根视图控制器”

我正在使用 UISplitViewController *splitViewController

如果是这样,修复它的方法是在 AppDelegate.m 文件中进行以下更改:

代替

 [self.window addSubview:[splitViewController view]];

[self.window setRootViewController:splitViewController];

在此之后shouldAutoRotate被调用并正常工作。

于 2013-01-28T21:41:10.553 回答
1

我正在使用 iOS 7,但我相信我的案例可能对其他人有帮助。

我有一个以 UITabBarController 为根的深层视图控制器层次结构。保证调用 shouldAutorotate 的唯一地方是在 UITabBarController 内部。所以我只是继承了 UITabBarController 并将我的旋转控制逻辑放在我的 shouldAutorotate 方法中。

于 2014-04-20T13:54:44.473 回答
0

我会这样做

如果您想检查当前方向,则将此行添加到您的 viewconrtoller.m 文件中

 #define isPortrait [[UIApplication sharedApplication] statusBarOrientation] == UIInterfaceOrientationPortrait || [[UIApplication sharedApplication] statusBarOrientation] == UIInterfaceOrientationPortraitUpsideDown

然后在你想检查方向的地方,写下如下的条件

- (void)viewDidLoad
{

        if(isPortrait)
        {
            //portrait mode....

            NSLog(@"its in IsPotraitMode");
        }
        else
        {
            //landscape mode....
            NSLog(@"its in IsLandscapeMode");
        }
}
于 2013-06-12T23:27:20.973 回答
0

如果您使用 UINavigationController 作为应用程序的基础。我创建了一个 UINavigationController 类别并将其命名为“UINavigationController+autoRotate”。把它放在你的 UINavigationController+autoRotate.h 中:

#import <UIKit/UIKit.h>

@interface UINavigationController (autoRotate)

-(BOOL)shouldAutorotate;
-(NSUInteger)supportedInterfaceOrientations;

@end

把它放在 UINavigationController+autoRotate.m 中:

#import "UINavigationController+autoRotate.h"

@implementation UINavigationController (autoRotate)

- (BOOL)shouldAutorotate
{
    return [self.visibleViewController shouldAutorotate];
}

- (NSUInteger)supportedInterfaceOrientations
{
    return [self.topViewController supportedInterfaceOrientations];
}

@end
于 2019-04-23T12:00:52.403 回答