AVPlayer crash when resizing window during fullscr

2019-03-25 07:26发布

问题:

I'm coding on an app where uses can watch a wide array of videos. I open the video in fullscreen on button tap and the user is able to use the playback controls to resize the window. The issue I'm having is that when the user is sharing his internet through hotspot there is a blue bar at the top of the app. When resizing the window at this point will cause a crash in the AVKit framework (I believe). Using Swift 2.3, Xcode 7.3.1. My phone, iPhone 6s, uses iOS 10 and I've also tried it on iOS 9 iPhone 6 Plus, same issue.

The crash:

Terminating app due to uncaught exception 'UIViewControllerHierarchyInconsistency', reason: 'child view controller:<AVFullScreenPlaybackControlsViewController: 0x102933000> should have parent view controller:<AVPlayerViewController: 0x10212d800> but actual parent is:<AVFullScreenViewController: 0x10884d900>'

My code:

private let playerController = AVPlayerViewController()
private var player: AVPlayer!

private func playVideo(media: Media) {

        player = AVPlayer(URL: NSURL(string: media.url)!)
        playerController.player = player

        presentViewController(playerController, animated: true, completion: {
            self.playerController.player?.play()
            self.playerController.delegate = self
        })

    }

If I don't share my internet on my phone (thus no blue bar) then it works fine, no issues whatsoever. Anyone managed to hide this blue bar, or experienced a similar issue?

回答1:

I have fixed it by this code:

@interface YourAVPlayerViewController : AVPlayerViewController
@end

@implementation YourAVPlayerViewController

 - (BOOL)prefersStatusBarHidden {
        return YES;
 }

@end


回答2:

As a workaround you can push on navigationControlelr stack or when presenting modally use this one:

@interface AVPlayerViewController ()
- (void)fullScreenButtonTapped:(id)arg1;
@end

@interface RCKPlayerViewController ()

@end

@implementation RCKPlayerViewController

- (void)fullScreenButtonTapped:(id)arg1 {
    if ([[UIApplication sharedApplication] statusBarFrame].size.height >= 40) {
        // Show alert that cannot enter full screen when in-call
    } else {
        [super fullScreenButtonTapped:arg1];
    }
}

@end

--

Then just use RCKPlayerViewController

AVPlayerViewController *playerViewController = [[RCKPlayerViewController alloc] init];
AVPlayerItem *playerItem = [AVPlayerItem playerItemWithURL:[NSURL URLWithString:videoStringURL]];
AVPlayer *player = [AVPlayer playerWithPlayerItem:playerItem];
playerViewController.player = player;

[self presentViewController:playerViewController animated:YES completion:^{
    [player play];
}];


回答3:

I wrote a small extension for AVPlayerViewController that fixes the issue app-wide:

// AVPlayerViewController.swift

import AVKit

extension AVPlayerViewController {

  // fixes app crash while using personal hotspot + watching a full screen video
  override open var prefersStatusBarHidden: Bool {
    return true
  }

}