2016-05-16 57 views
2

我正在播放使用AVPlayer的视频,这是我的应用程序中大约320x200的帧。 avplayer还有一个自定义的“全屏”按钮,如youtube应用播放器。我如何实现它,以便当应用程序处于肖像模式并且用户单击全屏按钮时,视频将旋转至全屏但处于横向模式?我尝试使用转换,它部分工作,因为当它在全屏模式下,如果用户切换设备为纵向; avplayer框架突然改变。我希望它能像YouTube应用一样工作,即在全屏模式下,即使用户旋转设备,也应该保持这种状态。关闭全屏后,只能恢复原始尺寸。由于应用程序的设计,我不想使用avplayerviewcontroller。预先感谢您的帮助。AVPlayer强制全屏风景模式

+1

当视频播放和全屏,设置'supportedInterfaceOrientations'仅景观 –

+0

这工作非常久远下面给出了答案,可你也看到我的意见给它一个问题关闭全屏实现? –

+0

澄清:您的问题是当您关闭全屏播放器时 - 较小的播放器不知道继续播放和从哪里播放? –

回答

3

伟大的问题!允许AVPLayerLayer进入全屏显示非常重要。相当数量的应用程序配置为单个视图处理纵向和横向,只是为了显示全屏视频?请。

变换和帧操作可以解决这个问题:

extension CGAffineTransform { 

    static let ninetyDegreeRotation = CGAffineTransform(rotationAngle: CGFloat(M_PI/2)) 
} 

extension AVPlayerLayer { 

    var fullScreenAnimationDuration: TimeInterval { 
     return 0.15 
    } 

    func minimizeToFrame(_ frame: CGRect) { 
     UIView.animate(withDuration: fullScreenAnimationDuration) { 
      self.setAffineTransform(.identity) 
      self.frame = frame 
     } 
    } 

    func goFullscreen() { 
     UIView.animate(withDuration: fullScreenAnimationDuration) { 
      self.setAffineTransform(.ninetyDegreeRotation) 
      self.frame = UIScreen.main.bounds 
     } 
    } 
} 

设置AVPlayerLayer的改变它的父的帧的帧。将原始帧保存在视图子类中,以将AVPLayerLayer最小化到原来的位置。这允许自动布局。

重要 - 只有当玩家处于视图子类中心时才有效。

不完整的例子:

class AVPlayerView: UIView { 

    fileprivate var avPlayerLayer: AVPlayerLayer { 
     return layer as! AVPlayerLayer 
    } 

    fileprivate var hasGoneFullScreen = false 
    fileprivate var isPlaying = false 
    fileprivate var originalFrame = CGRect.zero 

    func togglePlayback() { 
     if !hasGoneFullScreen { 
      originalFrame = frame 
      hasGoneFullScreen = true 
     } 

     isPlaying = !isPlaying 
     if isPlaying { 
      avPlayerLayer.goFullscreen() 
      avPlayerLayer.player?.play() 
     } else { 
      avPlayerLayer.player?.pause() 
      avPlayerLayer.minimizeToFrame(originalFrame) 
     } 
    } 
} 
3

在我看来,你应该创建一个FullScreenViewController,它总是被迫支持风景。然后,当按下“全屏”按钮并将AVPlayer实例传递给该视图控制器时,从当前视图控制器呈现该视图控制器,然后为AVPlayerLayer设置帧并继续播放。解散后,这将恢复正常,我的意思是你的“肖像”模式。

+0

这是我想到的以及可能的解决方案..希望看看有没有其他的方法。 –

+0

我用FullScreenViewController试过这个解决方案,并传递了具有AVPlayerLayer以及自定义控件UIView的容器UIView。到现在为止还挺好。然而,点击关闭全屏后,我关闭了FullScreenViewController,但播放器不会在我的演示视图中播放。我如何在FullScreenViewController中实现关闭全屏?因为我认为自从它被解散后,它的观点,即玩家容器视图被取消分配。 –

+0

部分代码:'FullScreenViewController * controller = [[FullScreenViewController alloc] init]; controller.view = self.playerContainer; //容器uiview [self presentViewController:controller animated:YES completion:nil];' –