必威-必威-欢迎您

必威,必威官网企业自成立以来,以策略先行,经营致胜,管理为本的商,业推广理念,一步一个脚印发展成为同类企业中经营范围最广,在行业内颇具影响力的企业。

勾选横屏和竖屏选项,那就是播放界面的旋转与

2019-09-16 00:01 来源:未知

背景: app内有贰个双页的分界面,然后某天运维说假若内部一页能支持横屏的话,对接的媒体就会给一整块显示器,然后要求就疑似此下来了(双页:一页协理横屏效果,另一页不援助)。

Device Orientation:设备方向

typedef NS_ENUM(NSInteger, UIDeviceOrientation) {
    UIDeviceOrientationUnknown,
    UIDeviceOrientationPortrait,            // Device oriented vertically, home button on the bottom
    UIDeviceOrientationPortraitUpsideDown,  // Device oriented vertically, home button on the top
    UIDeviceOrientationLandscapeLeft,       // Device oriented horizontally, home button on the right
    UIDeviceOrientationLandscapeRight,      // Device oriented horizontally, home button on the left
    UIDeviceOrientationFaceUp,              // Device oriented flat, face up
    UIDeviceOrientationFaceDown             // Device oriented flat, face down
}

必威 1显示屏旋转示例.jpeg

目前做项目境遇了显示屏旋转的主题材料,先说一下本身的须求吗:app除了录像播放那二个分界面辅助横竖屏外,其他分界面都只帮衬竖屏,并且在视屏播放那么些分界面,不协助手提式有线话机自动旋转,只可以通过点击放大开关,将播放器变为横屏放大。

本文显示器旋转方案只限于包容iOS8+

必威,接下去就�是查文书档案时间了,Duang,一下就查到了有未有,正是下面那八个法子。

UIInterfaceOrientation:分界面方向

typedef NS_ENUM(NSInteger, UIInterfaceOrientation) {
    UIInterfaceOrientationUnknown            = UIDeviceOrientationUnknown,
    UIInterfaceOrientationPortrait           = UIDeviceOrientationPortrait,
    UIInterfaceOrientationPortraitUpsideDown = UIDeviceOrientationPortraitUpsideDown,
    UIInterfaceOrientationLandscapeLeft      = UIDeviceOrientationLandscapeRight,
    UIInterfaceOrientationLandscapeRight     = UIDeviceOrientationLandscapeLeft
}

这两日抽空计算了须臾间iOS录像播放的主导用法,开掘那么些中还恐怕有三个我们鞭长莫及绕过的难题,那就是广播界面包车型大巴旋转与适配。的确,录制播放与游乐项目标App平日会碰着这么些的难点。由于现今接手的品种中有时涉及这块文化疏于总计,在查找了一部分质感后也开采都很糊涂,所以决定在此处重新整理一下。

一、关于orientation

显示屏旋转有两种:
1.装置的情理方向(device orientation),即app级别的;
2.分界面突显的大方向(interface orientation),即viewcontroller级其他。

1. 从APP档期的顺序聊起

应用程式常见的布局档期的顺序如下图所示:

必威 2

app layer.png

当工程目的开启了多少个显示器方向之后,具体类中关于显示屏旋转的布局其实只与最近显示屏呈现模块的最外层VC容器有关。
但出于频仍存在容器中一些VC针对显示屏旋转的本性化配置,所以需求开展从里层VC到外围容器的团团转状态传递。比如:

  • 里层UIViewController的配置
override func shouldAutorotate() -> Bool {
    return true
}

override func supportedInterfaceOrientations() -> UIInterfaceOrientationMask {
    return .Portrait
}

override func preferredInterfaceOrientationForPresentation() -> UIInterfaceOrientation {
    return .Portrait
}
  • 自定义UINavigationController的配置
override public func shouldAutorotate() -> Bool {
    return self.viewControllers.last?.shouldAutorotate() ?? false
}

override public func supportedInterfaceOrientations() -> UIInterfaceOrientationMask {
    return self.viewControllers.last?.supportedInterfaceOrientations() ?? .Portrait
}

override public func preferredInterfaceOrientationForPresentation() -> UIInterfaceOrientation {
    return self.viewControllers.last?.preferredInterfaceOrientationForPresentation() ?? .Portrait
}
  • 自定义UITabBarController的配置
override func shouldAutorotate() -> Bool {
    return self.selectedViewController?.shouldAutorotate() ?? false
}

override func supportedInterfaceOrientations() -> UIInterfaceOrientationMask {
    return self.selectedViewController?.supportedInterfaceOrientations() ?? .Portrait
}

override func preferredInterfaceOrientationForPresentation() -> UIInterfaceOrientation {
    return self.selectedViewController?.preferredInterfaceOrientationForPresentation() ?? .Portrait
}

//帮忙设施自动旋转

荧屏旋转的两个照看

// 硬件旋转通知,此时界面还未完成旋转可设置界面的旋转
UIDeviceOrientationDidChangeNotification
// 界面旋转通知,此时界面已经完成旋转
UIApplicationDidChangeStatusBarOrientationNotification

一、最令人纠结的二种枚举二、三种荧屏旋转的触及格局三、荧屏旋转调节的先行级四、开启显示屏旋转的全局权限五、开启荧屏旋转的一部分权限六、完毕要求:项目珍重分界面竖屏,部分界面横屏七、暗中同意横屏无效的难点八、关于旋转后的适配难点九、APP运营即全屏

二、怎么样设置orientation

咱们得以在info里面配置大家app辅助的动向音讯,也正是器具的物理方向,如下图,暗中认可境况下,Upside Down未有勾选,别的的都选了。

必威 3

图1.png

何以向来不勾选Upside Down呢?因为iphone的电话app是不协助Upside Down 的,假设你的app辅助Upside Down,当客户正在选拔你的app的时候,猝然有电话进来了,就能看出整个来电画面是本末倒置的,客户体验倒霉,所以不建议勾选。

根本来了!!!!因为我们要促成除了摄像播放页之外,其余分界面都只扶助竖屏,所以在Appdelegate.m 里面要写上如下代码:

#pragma mark 禁止横屏显示
#pragma mark 这个代理方法的优先级最高,self.allowRotation = 0,那么UI界面只支持竖屏;self.allowRotation = 1,根据自己需求返回相应的方向
-(UIInterfaceOrientationMask)application:(UIApplication *)application supportedInterfaceOrientationsForWindow:(UIWindow *)window
{
    if (self.allowRotation) {
   //根据自己需求,返回相应的方向
        return UIInterfaceOrientationMaskLandscapeRight;
    }
    return UIInterfaceOrientationMaskPortrait;
}

Appdelegate.h里如下:

必威 4

Appdelegate.h.png

咱俩在录像播放页面将allowRotation设置为YES就能够,代码如下:

 NTESAppDelegate *appdelagate = [UIApplication sharedApplication].delegate;
 appdelagate.allowRotation = YES;

便足以兑现,除录像播放页面外,其余都只支持竖屏展现的要求

2. AppDelegate配置

奉公守法上边的秘技配置好后,就足以随意的支配转屏了,但在少数情形下会存在难题,举个例证:要是A页面显示器锁定为竖屏,点击A页面的贰个开关跳转到了B页面(形式存在push跟present三种),B页面是足以拓宽横竖屏旋转的,当B页面旋转至横屏,那时候点击再次回到,会发觉A页面也造成横屏彰显了,何况不或许透过显示器旋转恢复到竖屏浮现。那时候上边这么些代理方法就排上用场了:

func application(application: UIApplication, supportedInterfaceOrientationsForWindow window: UIWindow?) -> UIInterfaceOrientationMask {    
    // 限定所有present的模态视图只能竖屏
    if self.window?.rootViewController?.presentedViewController != nil {
        return .Portrait
    }

    // 限定容器中当前展示的为RotateDetailViewController的实例时可以旋屏,其余页面只能竖屏
    let baseTabBarController = self.window?.rootViewController as? BaseTabBarController
    if ((baseTabBarController?.selectedViewController as? BaseNavigationController)?.topViewController is RotateDetailViewController {
        return .AllButUpsideDown
    } else {
        return .Portrait
    }
}

- shouldAutorotate

{

returnYES;

}

认清当前分界面方向

BOOL isPortrait = UIInterfaceOrientationIsPortrait([[UIApplication sharedApplication] statusBarOrientation]);
BOOL isLandscape = UIInterfaceOrientationIsLandscape([[UIApplication sharedApplication] statusBarOrientation]);

刚初步接触显示屏旋转那块文化的时候,最让人抓狂的可能就是二种有关的枚举类型了,它们正是UIDeviceOrientation、UIInterfaceOrientation、UIInterfaceOrientationMask。下边咱们本着三种本性进行深入分析:

三、根视图中的设置

这点很入眼,因为屡屡会被忽略掉,正是:必须在根视图设置相应的代码,不然播放器界面不能兑现真正的横屏放大的成效。小编的根视图是viewcontroller。(纵然完结效果与利益了,不过不领悟怎么,笔者那边就是设置了shouldAutorotate方法,可是自己的播放器分界面包车型大巴shouldAutorotate方法,还是不走,假设有知情的大神,还请不吝赐教!!)

必威 5

根视图的.m文件.png

3. 威吓旋屏

前提条件:该VC允许旋转

  • 强制竖屏
func forcePortrait(){
    let width = UIScreen.mainScreen().bounds.size.width
    let height = UIScreen.mainScreen().bounds.size.height

    let isLandscape = width > height
    if isLandscape {
        let device = UIDevice.currentDevice()
        let number = NSNumber(integer: UIInterfaceOrientation.Portrait.rawValue)
        device.setValue(number, forKey: "orientation")
    }
}
  • 强制横屏
func forceLandScape(){
    let width = UIScreen.mainScreen().bounds.size.width
    let height = UIScreen.mainScreen().bounds.size.height

    let isLandscape = width < height
    if isLandscape {
        let device = UIDevice.currentDevice()
        let number = NSNumber(integer: UIInterfaceOrientation.LandscapeRight.rawValue)
        device.setValue(number, forKey: "orientation")
    }
}

//援助横竖屏展现

单个页面是或不是可以旋转

@property(nonatomic, readonly) BOOL shouldAutorotate NS_AVAILABLE_IOS(6_0) __TVOS_PROHIBITED;
@property(nonatomic, readonly) UIInterfaceOrientationMask supportedInterfaceOrientations NS_AVAILABLE_IOS(6_0) __TVOS_PROHIBITED;

  • 面向Orientation的音信:随着显示屏的偏向转变

    • [UISCreen bounds]
    • [UISCreen applicationFrame]
    • Status bar frame notifications
    • Keyboard frame notifications
  • 显示器旋转时使得View有两样布局的兑现情势

// way1
- (void)viewWillTransitionToSize:(CGSize)size withTransitionCoordinator:(id<UIViewControllerTransitionCoordinator>)coordinator {
    [super viewWillTransitionToSize:size withTransitionCoordinator:coordinator];
    [coordinator animateAlongsideTransition:^(id<UIViewControllerTransitionCoordinatorContext>  _Nonnull context) {
        if (UIInterfaceOrientationIsPortrait([UIApplication sharedApplication].statusBarOrientation)) {
            _testTextField.frame = CGRectMake(50, 50, 150, 50);
            _testButton.frame = CGRectMake(50, 120, 150, 50);
        } else {
            _testTextField.frame = CGRectMake(50, 50, 150, 50);
            _testButton.frame = CGRectMake(220, 50, 150, 50);
        }
    } completion:^(id<UIViewControllerTransitionCoordinatorContext>  _Nonnull context) {

    }];
}

// way2
- (void)viewDidLayoutSubviews {
    [super viewDidLayoutSubviews];
    if (UIInterfaceOrientationIsPortrait([UIApplication sharedApplication].statusBarOrientation)) {
        _testTextField.frame = CGRectMake(50, 50, 150, 50);
        _testButton.frame = CGRectMake(50, 120, 150, 50);
    } else {
        _testTextField.frame = CGRectMake(50, 50, 150, 50);
        _testButton.frame = CGRectMake(220, 50, 150, 50);
    }
}
  • 旋转显示屏方向
NSNumber *value0 = [NSNumber numberWithInteger:UIDeviceOrientationUnknown];
[[UIDevice currentDevice] setValue:value0 forKey:@"orientation"];
NSNumber *value = [NSNumber numberWithInteger:UIDeviceOrientationLandscapeLeft];
[[UIDevice currentDevice] setValue:value forKey:@"orientation"];

  • 供给:应用软件总体不跟随设备的旋转来更动分界面包车型地铁主旋律,个别页面横屏显示

落实思路:首先APP应该帮助横屏和竖屏的展现,约等于说在TAOdysseyGETS中的Device Orientation选项勾选横屏和竖屏选项。假诺ViewController是根视图,那么当ViewController的- (BOOL)shouldAutorotate方法再次回到为YES的时候,分界面包车型大巴来头跟随设备方向调换。在NV结构(NavigationController上停放ViewController的结构)中需横屏展现的ViewController可不是根视图,此时分界面是或不是跟随设备旋转取决于根视图NavigationController的- (BOOL)shouldAutorotate方法的再次来到值。在这种气象中,可重写NavigationController的- (BOOL)shouldAutorotate方法再次来到Navigation栈中的最上端ViewController的shouldAutorotate,以此达到在单个页面随时间调节制其横屏的成效。横屏通过Key-Value的措施修改设备方一向到达指标。

一、勾选横屏和竖屏选项

必威 6

勾选横屏和竖屏选项

二、重写- (BOOL)shouldAutorotate重返栈顶调控器的shouldAutorotate

@interface MyNav : UINavigationController

@end

@implementation MyNav

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

@end

三、在就要横屏展现的ViewController中,重写- (BOOL)shouldAutorotate,入眼是用全局变量调整它的再次来到值

@interface LandscapeViewController () {
    BOOL _allowAutorotate;
}

- (BOOL)shouldAutorotate {
    [super shouldAutorotate];
    return _allowAutorotate;
}

四、通过Key-Value更换设备方向

_allowAutorotate = YES;
NSNumber *value0 = [NSNumber numberWithInteger:UIDeviceOrientationUnknown];
[[UIDevice currentDevice] setValue:value0 forKey:@"orientation"];
NSNumber *value = [NSNumber numberWithInteger:UIDeviceOrientationLandscapeLeft];
[[UIDevice currentDevice] setValue:value forKey:@"orientation"];
_allowAutorotate = NO;

1. 道具方向:UIDeviceOrientation

UIDeviceOrientation是硬件配备(三星、苹果平板等)自己的当前旋转方向,设备方向有7种(富含一种未知的情况),剖断设备的主旋律是以home键的职位作为参谋的,大家来看一下它们在源码中的定义如下:

//Portrait 表示纵向,Landscape 表示横向。typedef NS_ENUM(NSInteger, UIDeviceOrientation) { UIDeviceOrientationUnknown, UIDeviceOrientationPortrait, // Device oriented vertically, home button on the bottom UIDeviceOrientationPortraitUpsideDown, // Device oriented vertically, home button on the top UIDeviceOrientationLandscapeLeft, // Device oriented horizontally, home button on the right UIDeviceOrientationLandscapeRight, // Device oriented horizontally, home button on the left UIDeviceOrientationFaceUp, // Device oriented flat, face up UIDeviceOrientationFaceDown // Device oriented flat, face down } __TVOS_PROHIBITED;

设备方向只可以取值,不可能设置,收获道具当前旋转方向使用方法:[UIDevice currentDevice].orientation监测道具方向的变迁,大家得以在Appdelegate文件中采纳通告如下:

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(onDeviceOrientationDidChange) name:UIDeviceOrientationDidChangeNotification object:nil];[[UIDevice currentDevice] beginGeneratingDeviceOrientationNotifications]; - onDeviceOrientationDidChange{ //获取当前设备Device UIDevice *device = [UIDevice currentDevice] ; //识别当前设备的旋转方向 switch (device.orientation) { case UIDeviceOrientationFaceUp: NSLog(@"屏幕幕朝上平躺"); break; case UIDeviceOrientationFaceDown: NSLog(@"屏幕朝下平躺"); break; case UIDeviceOrientationUnknown: //系统当前无法识别设备朝向,可能是倾斜 NSLog; break; case UIDeviceOrientationLandscapeLeft: NSLog(@"屏幕向左橫置"); break; case UIDeviceOrientationLandscapeRight: NSLog(@"屏幕向右橫置"); break; case UIDeviceOrientationPortrait: NSLog; break; case UIDeviceOrientationPortraitUpsideDown: NSLog(@"屏幕直立,上下顛倒"); break; default: NSLog; break; } return YES;}

四、播放器视图中的设置

自家的需即使:点击按键,播放器横屏放大

必威 7

全屏按键点击事件.png

必威 8

脱离全屏的点击事件.png

总结

如上方案基本得以解决大部分的荧屏旋转场景了。假使APP的成品须要中注重为一定方向,只供给对弹出(present)模态视图举办旋转的话,能够仿效下边这篇文章:
iOS Orientations: Landscape orientation for only one View Controller
那样做会进一步惠及一些,但难点是这种方案对于push形式的场地并不适用,须要整合以上方案综合化解。

TAG标签:
版权声明:本文由必威发布于必威-编程,转载请注明出处:勾选横屏和竖屏选项,那就是播放界面的旋转与