繁体   English   中英

使用UITabBarController和/或UINavigationController时,仅将某些视图控制器限制/强制为特定方向

[英]Restrict/Force only some view controllers to specific orientations when using UITabBarController and/or UINavigationController

我在网上搜寻了很多东西,但是找不到确切的答案。 当将一个UIViewController嵌入到UINavigationController本身是UITabBarController一部分时,只有一种UIViewController支持横向模式的最佳方法是什么?

像这样的大多数解决方案都建议覆盖

-(NSUInteger)application:(UIApplication *)application supportedInterfaceOrientationsForWindow:(UIWindow *)window

AppDelegate 这在某种程度上是可行的,但是当从唯一一个支持横向模式的ViewController返回时,所有其他(非横向ViewController)也将处于横向。 他们不保持纵向。

我见过应用程序能正确实现这一点,所以我知道一定有可能实现。 例如,电影播放器​​应用程序通常仅是纵向的,但是实际的电影播放器​​视图以强制横向模式模态显示。 解散模态视图控制器后,基础视图控制器仍正确以纵向放置,

有什么提示吗?

经过大量研究,这是我的结论:

首先,我尝试实施

- (NSUInteger)application:(UIApplication *)application supportedInterfaceOrientationsForWindow:(UIWindow *)window;

如此处所述 AppDelegate中运行,适用于大多数情况。 但是除了感到“ hacky”外,还有一个严重的陷阱:例如,当显示AVPlayerViewController时,模式显示的视图控制器的变通方法(请参阅“模式控制器的小问题”一节)由于其实现了自己的关闭而失效方法,您无法将其设置为self.isPresented (不幸的是, viewWillDisappear:为时已晚)。

因此,我采用了为UITabBarControllerUINavigationController使用子类的另一种方法,它感觉更干净,但也更加冗长:

CustomNavigationController

CustomNavigationController.h

#import <UIKit/UIKit.h>

@interface CustomNavigationController : UINavigationController

@end

CustomNavigationController.m

#import "CustomNavigationController.h"

@implementation CustomNavigationController

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

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

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
    return [self.topViewController preferredInterfaceOrientationForPresentation];
}

@end

CustomTabBarController

CustomTabBarController.h

#import <UIKit/UIKit.h>

@interface CustomTabBarController : UITabBarController

@end

CustomTabBarController.m

#import "CustomTabBarController.h"

@implementation CustomTabBarController

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

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

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
    return [self.selectedViewController preferredInterfaceOrientationForPresentation];
}

@end

之后,只需将以下代码添加到UIViewControllers

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation {
    // Presents the `UIViewController` in landscape orientation when it is first displayed 
    return UIInterfaceOrientationLandscapeLeft;
}

- (NSUInteger)supportedInterfaceOrientations {
    // Allows all other orientations (except upside-down)
    return UIInterfaceOrientationMaskAllButUpsideDown;
}

现在,您可以基于每个视图控制器确定首选和支持的方向。 请注意,我没有在我的视图控制器中实现shouldAutorotate ,因为它默认为YES,这是您将视图控制器强制设置为某个方向时想要的(是的,它们应该自动旋转为唯一受支持的方向)。

调用链如下所示:

  • 要求CustomTabBarController作为窗口的rootViewController ,以获取受支持/首选的方向
  • CustomTabBarController依次询问其selectedViewController (当前选定选项卡的视图控制器),恰好是我的CustomNavigationController
  • 所述CustomNavigationController询问嵌入topViewController ,这是最后的实际UIViewController实现上述方法的

您仍然需要在构建目标中允许所有设备方向。 当然,您需要更新情节提要/ xib /类以使用这些子类,而不是标准的UINavigationControllerUITabBarController类。

这种方法的唯一缺点是,至少就我而言,我必须将这些方法添加到我的所有视图控制器中,以使大多数视图控制器仅是纵向的并且具有横向功能。 但是恕我直言,这绝对值得!

您应该将上面的代码编写到UINavigationController子类中。 您应该定义应用程序方向,并使用if语句分隔视图控制器方向。

-(BOOL)shouldAutorotate {

    if ([[self.viewControllers lastObject] isKindOfClass:[UIViewController class]] ) {

        return [[self.viewControllers lastObject] shouldAutorotate];
    }

    return NO;

}
- (NSUInteger)supportedInterfaceOrientations {

    if ([[self.viewControllers lastObject] isKindOfClass:[UIViewController class]]) {

        return [[self.viewControllers lastObject] supportedInterfaceOrientations];
    }

    return UIInterfaceOrientationMaskPortrait;
}

- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation {


    return UIInterfaceOrientationPortrait;

}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM