Changeset 277424 in webkit
- Timestamp:
- May 12, 2021, 10:37:17 PM (5 years ago)
- Location:
- trunk/Source/WebCore
- Files:
-
- 6 edited
-
ChangeLog (modified) (1 diff)
-
platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaSourceAVFObjC.mm (modified) (1 diff)
-
platform/graphics/avfoundation/objc/MediaSourcePrivateAVFObjC.h (modified) (1 diff)
-
platform/graphics/avfoundation/objc/MediaSourcePrivateAVFObjC.mm (modified) (1 diff)
-
platform/graphics/avfoundation/objc/SourceBufferPrivateAVFObjC.h (modified) (2 diffs)
-
platform/graphics/avfoundation/objc/SourceBufferPrivateAVFObjC.mm (modified) (3 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebCore/ChangeLog
r277420 r277424 1 2021-05-12 Peng Liu <peng.liu6@apple.com> 2 3 [iPad] SourceBufferPrivateAVFObjC should not report an error to the web page when the video playback is interrupted 4 https://bugs.webkit.org/show_bug.cgi?id=225620 5 6 Reviewed by Jer Noble. 7 8 If `SourceBufferPrivateAVFObjC` reports an error to a web page when 9 `AVSampleBufferDisplayLayer` reports `AVErrorOperationInterrupted` (the playback 10 was interrupted), the web page will likely destroy the video player (and teardown 11 the video element). That behavior will lead to an empty picture-in-picture window 12 if the video was playing in picture-in-picture. 13 14 With this patch, `SourceBufferPrivateAVFObjC` will not report an error to the 15 web page in case of playback interruption. Instead, it takes a note that 16 the playback was interrupted, so that when we try to resume the playback later, 17 it will flush the `AVSampleBufferDisplayLayer` to recover the playback state. 18 19 In addition, we need to enqueue an IDR frame first before we enqueue more 20 samples after flushing the `AVSampleBufferDisplayLayer`. That is guaranteed 21 by `SourceBufferPrivate::reenqueSamples()`. 22 23 * platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaSourceAVFObjC.mm: 24 (WebCore::MediaPlayerPrivateMediaSourceAVFObjC::playInternal): 25 * platform/graphics/avfoundation/objc/MediaSourcePrivateAVFObjC.h: 26 * platform/graphics/avfoundation/objc/MediaSourcePrivateAVFObjC.mm: 27 (WebCore::MediaSourcePrivateAVFObjC::flushActiveSourceBuffersIfNeeded): 28 * platform/graphics/avfoundation/objc/SourceBufferPrivateAVFObjC.h: 29 * platform/graphics/avfoundation/objc/SourceBufferPrivateAVFObjC.mm: 30 (WebCore::SourceBufferPrivateAVFObjC::flushIfNeeded): 31 (WebCore::SourceBufferPrivateAVFObjC::layerDidReceiveError): 32 (WebCore::SourceBufferPrivateAVFObjC::isReadyForMoreSamples): 33 1 34 2021-05-12 Chris Dumez <cdumez@apple.com> 2 35 -
trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaSourceAVFObjC.mm
r277365 r277424 323 323 324 324 ALWAYS_LOG(LOGIDENTIFIER); 325 #if PLATFORM(IOS_FAMILY) 326 m_mediaSourcePrivate->flushActiveSourceBuffersIfNeeded(); 327 #endif 325 328 m_playing = true; 326 329 if (shouldBePlaying()) -
trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaSourcePrivateAVFObjC.h
r272696 r277424 94 94 void setDecompressionSession(WebCoreDecompressionSession*); 95 95 96 #if PLATFORM(IOS_FAMILY) 97 void flushActiveSourceBuffersIfNeeded(); 98 #endif 99 96 100 #if ENABLE(ENCRYPTED_MEDIA) 97 101 void cdmInstanceAttached(CDMInstance&); -
trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaSourcePrivateAVFObjC.mm
r271530 r277424 283 283 } 284 284 285 #if PLATFORM(IOS_FAMILY) 286 void MediaSourcePrivateAVFObjC::flushActiveSourceBuffersIfNeeded() 287 { 288 for (auto* sourceBuffer : m_activeSourceBuffers) 289 sourceBuffer->flushIfNeeded(); 290 } 291 #endif 292 285 293 #if ENABLE(ENCRYPTED_MEDIA) 286 294 void MediaSourcePrivateAVFObjC::cdmInstanceAttached(CDMInstance& instance) -
trunk/Source/WebCore/platform/graphics/avfoundation/objc/SourceBufferPrivateAVFObjC.h
r276828 r277424 110 110 111 111 void flush(); 112 #if PLATFORM(IOS_FAMILY) 113 void flushIfNeeded(); 114 #endif 112 115 113 116 void registerForErrorNotifications(SourceBufferPrivateAVFObjCErrorClient*); … … 198 201 ALLOW_NEW_API_WITHOUT_GUARDS_END 199 202 RetainPtr<WebAVSampleBufferErrorListener> m_errorListener; 203 #if PLATFORM(IOS_FAMILY) 204 bool m_displayLayerWasInterrupted { false }; 205 #endif 200 206 RetainPtr<NSError> m_hdcpError; 201 207 Box<BinarySemaphore> m_hasSessionSemaphore; -
trunk/Source/WebCore/platform/graphics/avfoundation/objc/SourceBufferPrivateAVFObjC.mm
r277246 r277424 929 929 } 930 930 931 #if PLATFORM(IOS_FAMILY) 932 void SourceBufferPrivateAVFObjC::flushIfNeeded() 933 { 934 if (!m_displayLayerWasInterrupted) 935 return; 936 937 m_displayLayerWasInterrupted = false; 938 if (m_videoTracks.size()) 939 flushVideo(); 940 941 // We initiatively enqueue samples instead of waiting for the 942 // media data requests from m_decompressionSession and m_displayLayer. 943 // In addition, we need to enqueue a sync sample (IDR video frame) first. 944 if (m_decompressionSession) 945 m_decompressionSession->stopRequestingMediaData(); 946 [m_displayLayer stopRequestingMediaData]; 947 948 reenqueSamples(AtomString::number(m_enabledVideoTrackID)); 949 } 950 #endif 951 931 952 void SourceBufferPrivateAVFObjC::registerForErrorNotifications(SourceBufferPrivateAVFObjCErrorClient* client) 932 953 { … … 944 965 { 945 966 ERROR_LOG(LOGIDENTIFIER, [[error description] UTF8String]); 967 968 #if PLATFORM(IOS_FAMILY) 969 if ([layer status] == AVQueuedSampleBufferRenderingStatusFailed && [[error domain] isEqualToString:@"AVFoundationErrorDomain"] && [error code] == AVErrorOperationInterrupted) { 970 m_displayLayerWasInterrupted = true; 971 return; 972 } 973 #endif 946 974 947 975 // FIXME(142246): Remove the following once <rdar://problem/20027434> is resolved. … … 1175 1203 auto trackID = parseIntegerAllowingTrailingJunk<uint64_t>(trackIDString).valueOr(0); 1176 1204 if (trackID == m_enabledVideoTrackID) { 1205 #if PLATFORM(IOS_FAMILY) 1206 if (m_displayLayerWasInterrupted) 1207 return false; 1208 #endif 1209 1177 1210 if (m_decompressionSession) 1178 1211 return m_decompressionSession->isReadyForMoreMediaData();
Note:
See TracChangeset
for help on using the changeset viewer.