Merge pull request #1325 from Khan/pip

Implement picture in picture for iOS
This commit is contained in:
Hampton Maxwell
2019-02-18 22:13:02 -08:00
committed by GitHub
5 changed files with 153 additions and 1 deletions

View File

@@ -27,6 +27,8 @@ static int const RCTVideoUnset = -1;
AVPlayer *_player;
AVPlayerItem *_playerItem;
NSDictionary *_source;
AVPictureInPictureController *_pipController;
void (^__strong _Nonnull _restoreUserInterfaceForPIPStopCompletionHandler)(BOOL);
BOOL _playerItemObserversSet;
BOOL _playerBufferEmpty;
AVPlayerLayer *_playerLayer;
@@ -64,6 +66,7 @@ static int const RCTVideoUnset = -1;
BOOL _playbackStalled;
BOOL _playInBackground;
BOOL _playWhenInactive;
BOOL _pictureInPicture;
NSString * _ignoreSilentSwitch;
NSString * _resizeMode;
BOOL _fullscreen;
@@ -100,7 +103,9 @@ static int const RCTVideoUnset = -1;
_playInBackground = false;
_allowsExternalPlayback = YES;
_playWhenInactive = false;
_pictureInPicture = false;
_ignoreSilentSwitch = @"inherit"; // inherit, ignore, obey
_restoreUserInterfaceForPIPStopCompletionHandler = NULL;
#if __has_include(<react-native-video/RCTVideoCache.h>)
_videoCache = [RCTVideoCache sharedInstance];
#endif
@@ -786,6 +791,40 @@ static int const RCTVideoUnset = -1;
_playWhenInactive = playWhenInactive;
}
- (void)setPictureInPicture:(BOOL)pictureInPicture
{
if (_pictureInPicture == pictureInPicture) {
return;
}
_pictureInPicture = pictureInPicture;
if (_pipController && _pictureInPicture && ![_pipController isPictureInPictureActive]) {
dispatch_async(dispatch_get_main_queue(), ^{
[_pipController startPictureInPicture];
});
} else if (_pipController && !_pictureInPicture && [_pipController isPictureInPictureActive]) {
dispatch_async(dispatch_get_main_queue(), ^{
[_pipController stopPictureInPicture];
});
}
}
- (void)setRestoreUserInterfaceForPIPStopCompletionHandler:(BOOL)restore
{
if (_restoreUserInterfaceForPIPStopCompletionHandler != NULL) {
_restoreUserInterfaceForPIPStopCompletionHandler(restore);
_restoreUserInterfaceForPIPStopCompletionHandler = NULL;
}
}
- (void)setupPipController {
if (!_pipController && _playerLayer && [AVPictureInPictureController isPictureInPictureSupported]) {
// Create new controller passing reference to the AVPlayerLayer
_pipController = [[AVPictureInPictureController alloc] initWithPlayerLayer:_playerLayer];
_pipController.delegate = self;
}
}
- (void)setIgnoreSilentSwitch:(NSString *)ignoreSilentSwitch
{
_ignoreSilentSwitch = ignoreSilentSwitch;
@@ -1240,6 +1279,8 @@ static int const RCTVideoUnset = -1;
[self.layer addSublayer:_playerLayer];
self.layer.needsDisplayOnBoundsChange = YES;
[self setupPipController];
}
}
@@ -1496,4 +1537,42 @@ static int const RCTVideoUnset = -1;
return array[0];
}
#pragma mark - Picture in Picture
- (void)pictureInPictureControllerDidStopPictureInPicture:(AVPictureInPictureController *)pictureInPictureController {
if (self.onPictureInPictureStatusChanged) {
self.onPictureInPictureStatusChanged(@{
@"isActive": [NSNumber numberWithBool:false]
});
}
}
- (void)pictureInPictureControllerDidStartPictureInPicture:(AVPictureInPictureController *)pictureInPictureController {
if (self.onPictureInPictureStatusChanged) {
self.onPictureInPictureStatusChanged(@{
@"isActive": [NSNumber numberWithBool:true]
});
}
}
- (void)pictureInPictureControllerWillStopPictureInPicture:(AVPictureInPictureController *)pictureInPictureController {
}
- (void)pictureInPictureControllerWillStartPictureInPicture:(AVPictureInPictureController *)pictureInPictureController {
}
- (void)pictureInPictureController:(AVPictureInPictureController *)pictureInPictureController failedToStartPictureInPictureWithError:(NSError *)error {
}
- (void)pictureInPictureController:(AVPictureInPictureController *)pictureInPictureController restoreUserInterfaceForPictureInPictureStopWithCompletionHandler:(void (^)(BOOL))completionHandler {
NSAssert(_restoreUserInterfaceForPIPStopCompletionHandler == NULL, @"restoreUserInterfaceForPIPStopCompletionHandler was not called after picture in picture was exited.");
if (self.onRestoreUserInterfaceForPictureInPictureStop) {
self.onRestoreUserInterfaceForPictureInPictureStop(@{});
}
_restoreUserInterfaceForPIPStopCompletionHandler = completionHandler;
}
@end