diff --git a/packages/video_player/video_player_avfoundation/CHANGELOG.md b/packages/video_player/video_player_avfoundation/CHANGELOG.md index e8642b6e04..5e7d48ef4a 100644 --- a/packages/video_player/video_player_avfoundation/CHANGELOG.md +++ b/packages/video_player/video_player_avfoundation/CHANGELOG.md @@ -1,3 +1,7 @@ +## 2.4.8 + +* Fixes missing `isPlaybackLikelyToKeepUp` check for iOS video player `bufferingEnd` event and `bufferingStart` event. + ## 2.4.7 * Updates minimum supported SDK version to Flutter 3.3/Dart 2.18. diff --git a/packages/video_player/video_player_avfoundation/example/ios/RunnerTests/VideoPlayerTests.m b/packages/video_player/video_player_avfoundation/example/ios/RunnerTests/VideoPlayerTests.m index a9d7eac073..17c46ad6f5 100644 --- a/packages/video_player/video_player_avfoundation/example/ios/RunnerTests/VideoPlayerTests.m +++ b/packages/video_player/video_player_avfoundation/example/ios/RunnerTests/VideoPlayerTests.m @@ -207,6 +207,52 @@ [self waitForExpectationsWithTimeout:30.0 handler:nil]; } +- (void)testBufferingStateFromPlayer { + NSObject *registry = + (NSObject *)[[UIApplication sharedApplication] delegate]; + NSObject *registrar = + [registry registrarForPlugin:@"testLiveStreamBufferEndFromPlayer"]; + FLTVideoPlayerPlugin *videoPlayerPlugin = + (FLTVideoPlayerPlugin *)[[FLTVideoPlayerPlugin alloc] initWithRegistrar:registrar]; + + FlutterError *error; + [videoPlayerPlugin initialize:&error]; + XCTAssertNil(error); + + FLTCreateMessage *create = [FLTCreateMessage + makeWithAsset:nil + uri:@"https://flutter.github.io/assets-for-api-docs/assets/videos/bee.mp4" + packageName:nil + formatHint:nil + httpHeaders:@{}]; + FLTTextureMessage *textureMessage = [videoPlayerPlugin create:create error:&error]; + XCTAssertNil(error); + XCTAssertNotNil(textureMessage); + FLTVideoPlayer *player = videoPlayerPlugin.playersByTextureId[textureMessage.textureId]; + XCTAssertNotNil(player); + AVPlayer *avPlayer = player.player; + [avPlayer play]; + + [player onListenWithArguments:nil + eventSink:^(NSDictionary *event) { + if ([event[@"event"] isEqualToString:@"bufferingEnd"]) { + XCTAssertTrue(avPlayer.currentItem.isPlaybackLikelyToKeepUp); + } + + if ([event[@"event"] isEqualToString:@"bufferingStart"]) { + XCTAssertFalse(avPlayer.currentItem.isPlaybackLikelyToKeepUp); + } + }]; + XCTestExpectation *bufferingStateExpectation = + [self expectationWithDescription:@"bufferingState"]; + NSTimeInterval timeout = 10; + dispatch_time_t delay = dispatch_time(DISPATCH_TIME_NOW, timeout * NSEC_PER_SEC); + dispatch_after(delay, dispatch_get_main_queue(), ^{ + [bufferingStateExpectation fulfill]; + }); + [self waitForExpectationsWithTimeout:timeout + 1 handler:nil]; +} + - (void)testVideoControls { NSObject *registry = (NSObject *)[[UIApplication sharedApplication] delegate]; diff --git a/packages/video_player/video_player_avfoundation/ios/Classes/FLTVideoPlayerPlugin.m b/packages/video_player/video_player_avfoundation/ios/Classes/FLTVideoPlayerPlugin.m index ba45d4d3ea..1c37d630ea 100644 --- a/packages/video_player/video_player_avfoundation/ios/Classes/FLTVideoPlayerPlugin.m +++ b/packages/video_player/video_player_avfoundation/ios/Classes/FLTVideoPlayerPlugin.m @@ -72,8 +72,6 @@ static void *statusContext = &statusContext; static void *presentationSizeContext = &presentationSizeContext; static void *durationContext = &durationContext; static void *playbackLikelyToKeepUpContext = &playbackLikelyToKeepUpContext; -static void *playbackBufferEmptyContext = &playbackBufferEmptyContext; -static void *playbackBufferFullContext = &playbackBufferFullContext; static void *rateContext = &rateContext; @implementation FLTVideoPlayer @@ -108,14 +106,6 @@ static void *rateContext = &rateContext; forKeyPath:@"playbackLikelyToKeepUp" options:NSKeyValueObservingOptionInitial | NSKeyValueObservingOptionNew context:playbackLikelyToKeepUpContext]; - [item addObserver:self - forKeyPath:@"playbackBufferEmpty" - options:NSKeyValueObservingOptionInitial | NSKeyValueObservingOptionNew - context:playbackBufferEmptyContext]; - [item addObserver:self - forKeyPath:@"playbackBufferFull" - options:NSKeyValueObservingOptionInitial | NSKeyValueObservingOptionNew - context:playbackBufferFullContext]; // Add observer to AVPlayer instead of AVPlayerItem since the AVPlayerItem does not have a "rate" // property @@ -330,19 +320,15 @@ NS_INLINE UIViewController *rootViewController(void) { [self updatePlayingState]; } } else if (context == playbackLikelyToKeepUpContext) { + [self updatePlayingState]; if ([[_player currentItem] isPlaybackLikelyToKeepUp]) { - [self updatePlayingState]; if (_eventSink != nil) { _eventSink(@{@"event" : @"bufferingEnd"}); } - } - } else if (context == playbackBufferEmptyContext) { - if (_eventSink != nil) { - _eventSink(@{@"event" : @"bufferingStart"}); - } - } else if (context == playbackBufferFullContext) { - if (_eventSink != nil) { - _eventSink(@{@"event" : @"bufferingEnd"}); + } else { + if (_eventSink != nil) { + _eventSink(@{@"event" : @"bufferingStart"}); + } } } else if (context == rateContext) { // Important: Make sure to cast the object to AVPlayer when observing the rate property, @@ -528,8 +514,6 @@ NS_INLINE UIViewController *rootViewController(void) { [currentItem removeObserver:self forKeyPath:@"presentationSize"]; [currentItem removeObserver:self forKeyPath:@"duration"]; [currentItem removeObserver:self forKeyPath:@"playbackLikelyToKeepUp"]; - [currentItem removeObserver:self forKeyPath:@"playbackBufferEmpty"]; - [currentItem removeObserver:self forKeyPath:@"playbackBufferFull"]; [self.player replaceCurrentItemWithPlayerItem:nil]; [[NSNotificationCenter defaultCenter] removeObserver:self]; diff --git a/packages/video_player/video_player_avfoundation/pubspec.yaml b/packages/video_player/video_player_avfoundation/pubspec.yaml index a0c2f4ebae..5c83393057 100644 --- a/packages/video_player/video_player_avfoundation/pubspec.yaml +++ b/packages/video_player/video_player_avfoundation/pubspec.yaml @@ -2,7 +2,7 @@ name: video_player_avfoundation description: iOS implementation of the video_player plugin. repository: https://github.com/flutter/packages/tree/main/packages/video_player/video_player_avfoundation issue_tracker: https://github.com/flutter/flutter/issues?q=is%3Aissue+is%3Aopen+label%3A%22p%3A+video_player%22 -version: 2.4.7 +version: 2.4.8 environment: sdk: ">=2.18.0 <4.0.0"