From d5feb3a4898779be4d596217910c1fc6d861ec92 Mon Sep 17 00:00:00 2001 From: Ben Hagen Date: Fri, 12 Nov 2021 19:12:19 +0100 Subject: [PATCH] Use synchronized --- .../macos/Classes/FLTVideoPlayerPlugin.m | 69 +++++++++++-------- 1 file changed, 40 insertions(+), 29 deletions(-) diff --git a/packages/video_player/video_player_macos/macos/Classes/FLTVideoPlayerPlugin.m b/packages/video_player/video_player_macos/macos/Classes/FLTVideoPlayerPlugin.m index f223340aaf2b..151e97f9e4b0 100644 --- a/packages/video_player/video_player_macos/macos/Classes/FLTVideoPlayerPlugin.m +++ b/packages/video_player/video_player_macos/macos/Classes/FLTVideoPlayerPlugin.m @@ -172,8 +172,10 @@ - (void)notifyIfFrameAvailable { } else { CVPixelBufferRef pixelBuffer = [_videoOutput copyPixelBufferForItemTime:outputItemTime itemTimeForDisplay:NULL]; if (pixelBuffer != NULL) { - CVBufferRelease(_lastValidFrame); - _lastValidFrame = pixelBuffer; + @synchronized (self) { + CVBufferRelease(_lastValidFrame); + _lastValidFrame = pixelBuffer; + } } [_frameUpdater notifyFrameAvailable]; } @@ -185,9 +187,7 @@ static CVReturn OnDisplayLink(CVDisplayLinkRef CV_NONNULL displayLink, CVOptionFlags* CV_NONNULL flagsOut, void* CV_NULLABLE displayLinkContext) { __weak FLTVideoPlayer* video_player = (__bridge FLTVideoPlayer*)(displayLinkContext); - dispatch_async(dispatch_get_main_queue(), ^{ - [video_player notifyIfFrameAvailable]; - }); + [video_player notifyIfFrameAvailable]; return kCVReturnSuccess; } @@ -403,9 +403,7 @@ - (void)seekTo:(int)location { [_player seekToTime:CMTimeMake(location, 1000) toleranceBefore:kCMTimeZero toleranceAfter:kCMTimeZero]; - dispatch_async(dispatch_get_main_queue(), ^{ - [self notifyIfFrameAvailable]; - }); + [self notifyIfFrameAvailable]; } - (void)setIsLooping:(bool)isLooping { @@ -445,28 +443,41 @@ - (CVPixelBufferRef)copyPixelBuffer { // // Unlike on iOS, the macOS embedder does show the last frame when // we return NULL from `copyPixelBuffer`. - CVPixelBufferLockBaseAddress(_lastValidFrame, kCVPixelBufferLock_ReadOnly); - int bufferWidth = (int)CVPixelBufferGetWidth(_lastValidFrame); - int bufferHeight = (int)CVPixelBufferGetHeight(_lastValidFrame); - size_t bytesPerRow = CVPixelBufferGetBytesPerRow(_lastValidFrame); - uint8_t *baseAddress = CVPixelBufferGetBaseAddress(_lastValidFrame); - NSDictionary* pixBuffAttributes = @{ - (id)kCVPixelBufferPixelFormatTypeKey : @(kCVPixelFormatType_32BGRA), - (id)kCVPixelBufferIOSurfacePropertiesKey : @{}, - (id)kCVPixelBufferOpenGLCompatibilityKey : @YES, - (id)kCVPixelBufferMetalCompatibilityKey : @YES, - }; - - CVPixelBufferRef pixelBufferCopy = NULL; - CVPixelBufferCreate(kCFAllocatorDefault, bufferWidth, bufferHeight,kCVPixelFormatType_32BGRA, - CFBridgingRetain(pixBuffAttributes), &pixelBufferCopy); - CVPixelBufferLockBaseAddress(pixelBufferCopy, 0); - uint8_t *copyBaseAddress = CVPixelBufferGetBaseAddress(pixelBufferCopy); - memcpy(copyBaseAddress, baseAddress, bufferHeight * bytesPerRow); - CVPixelBufferUnlockBaseAddress(_lastValidFrame, kCVPixelBufferLock_ReadOnly); - CVPixelBufferUnlockBaseAddress(pixelBufferCopy, 0); - return pixelBufferCopy; + if (_lastValidFrame == NULL) { + return NULL; + } + + @synchronized (self) { + CVPixelBufferLockBaseAddress(_lastValidFrame, kCVPixelBufferLock_ReadOnly); + int bufferWidth = (int)CVPixelBufferGetWidth(_lastValidFrame); + int bufferHeight = (int)CVPixelBufferGetHeight(_lastValidFrame); + size_t bytesPerRow = CVPixelBufferGetBytesPerRow(_lastValidFrame); + uint8_t *baseAddress = CVPixelBufferGetBaseAddress(_lastValidFrame); + + if (baseAddress == NULL) { + NSLog(@"----> baseadress is NULL"); + return NULL; + } + + NSDictionary* pixBuffAttributes = @{ + (id)kCVPixelBufferPixelFormatTypeKey : @(kCVPixelFormatType_32BGRA), + (id)kCVPixelBufferIOSurfacePropertiesKey : @{}, + (id)kCVPixelBufferOpenGLCompatibilityKey : @YES, + (id)kCVPixelBufferMetalCompatibilityKey : @YES, + }; + + CVPixelBufferRef pixelBufferCopy = NULL; + CVPixelBufferCreate(kCFAllocatorDefault, bufferWidth, bufferHeight,kCVPixelFormatType_32BGRA, + CFBridgingRetain(pixBuffAttributes), &pixelBufferCopy); + CVPixelBufferLockBaseAddress(pixelBufferCopy, 0); + uint8_t *copyBaseAddress = CVPixelBufferGetBaseAddress(pixelBufferCopy); + memcpy(copyBaseAddress, baseAddress, bufferHeight * bytesPerRow); + + CVPixelBufferUnlockBaseAddress(_lastValidFrame, kCVPixelBufferLock_ReadOnly); + CVPixelBufferUnlockBaseAddress(pixelBufferCopy, 0); + return pixelBufferCopy; + } } - (void)onTextureUnregistered:(NSObject*)texture {