<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[208851] trunk/Source/WebCore</title>
</head>
<body>
<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; }
#msg dl a { font-weight: bold}
#msg dl a:link { color:#fc3; }
#msg dl a:active { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/208851">208851</a></dd>
<dt>Author</dt> <dd>eric.carlson@apple.com</dd>
<dt>Date</dt> <dd>2016-11-17 10:43:40 -0800 (Thu, 17 Nov 2016)</dd>
</dl>
<h3>Log Message</h3>
<pre>[MediaStream][Mac] Use AVCapturePreview object for camera/microphone rendering
https://bugs.webkit.org/show_bug.cgi?id=164837
<rdar://problem/29297727>
Reviewed by Jer Noble.
No new tests, the real capture devices can not be used in layout tests.
* WebCore.xcodeproj/project.pbxproj:
Drive-by fix: clear m_settingMediaStreamSrcObject when the media player is destroyed unless
that happens as a side effect of setting video.srcObject.
* html/HTMLMediaElement.cpp:
(WebCore::HTMLMediaElement::setSrcObject):
(WebCore::HTMLMediaElement::clearMediaPlayer):
* html/HTMLMediaElement.h:
Add support for realtime media source that vend a preview interface, while keeping support
for those that do not (e.g. the mock capture devices).
* platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.h:
* platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.mm:
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::MediaPlayerPrivateMediaStreamAVFObjC):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::isAvailable):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::enqueueVideoSampleBuffer):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::prepareVideoSampleBufferFromTrack):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::ensureLayer):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::destroyLayer):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::platformLayer):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::currentDisplayMode):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::play):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::pause):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::internalSetVolume):
(WebCore::MediaPlayerPrivateMediaStreamAVFObjC::updateTracks):
* platform/mediastream/MediaStreamPrivate.cpp:
(WebCore::MediaStreamPrivate::platformLayer): Deleted, no longer used.
* platform/mediastream/MediaStreamPrivate.h:
Enable/disable the preview when available.
* platform/mediastream/MediaStreamTrackPrivate.cpp:
(WebCore::MediaStreamTrackPrivate::setEnabled):
(WebCore::MediaStreamTrackPrivate::endTrack):
(WebCore::MediaStreamTrackPrivate::preview):
* platform/mediastream/MediaStreamTrackPrivate.h:
* platform/mediastream/RealtimeMediaSource.h:
(WebCore::RealtimeMediaSource::preview):
(WebCore::RealtimeMediaSource::createWeakPtr):
(WebCore::RealtimeMediaSource::platformLayer): Deleted.
Define a realtime media source preview interface.
* platform/mediastream/RealtimeMediaSourcePreview.h: Added.
(WebCore::RealtimeMediaSourcePreview::~RealtimeMediaSourcePreview):
(WebCore::RealtimeMediaSourcePreview::invalidate):
(WebCore::RealtimeMediaSourcePreview::createWeakPtr):
(WebCore::RealtimeMediaSourcePreview::RealtimeMediaSourcePreview):
Implement the preview interface.
* platform/mediastream/mac/AVAudioCaptureSource.h:
* platform/mediastream/mac/AVAudioCaptureSource.mm:
(WebCore::AVAudioSourcePreview::create):
(WebCore::AVAudioSourcePreview::AVAudioSourcePreview):
(WebCore::AVAudioSourcePreview::invalidate):
(WebCore::AVAudioSourcePreview::play):
(WebCore::AVAudioSourcePreview::pause):
(WebCore::AVAudioSourcePreview::setEnabled):
(WebCore::AVAudioSourcePreview::setVolume):
(WebCore::AVAudioSourcePreview::updateState):
(WebCore::AVAudioCaptureSource::createPreview):
* platform/mediastream/mac/AVMediaCaptureSource.h:
(WebCore::AVMediaCaptureSource::createWeakPtr):
* platform/mediastream/mac/AVMediaCaptureSource.mm:
(WebCore::AVMediaCaptureSource::AVMediaCaptureSource):
(WebCore::AVMediaCaptureSource::reset):
(WebCore::AVMediaCaptureSource::preview):
(WebCore::AVMediaCaptureSource::removePreview):
(WebCore::AVMediaSourcePreview::AVMediaSourcePreview):
(WebCore::AVMediaSourcePreview::~AVMediaSourcePreview):
(WebCore::AVMediaSourcePreview::invalidate):
* platform/mediastream/mac/AVVideoCaptureSource.h:
* platform/mediastream/mac/AVVideoCaptureSource.mm:
(WebCore::AVVideoSourcePreview::create):
(WebCore::AVVideoSourcePreview::AVVideoSourcePreview):
(WebCore::AVVideoSourcePreview::invalidate):
(WebCore::AVVideoSourcePreview::play):
(WebCore::AVVideoSourcePreview::pause):
(WebCore::AVVideoSourcePreview::setPaused):
(WebCore::AVVideoSourcePreview::setEnabled):
(WebCore::AVVideoCaptureSource::shutdownCaptureSession):
(WebCore::AVVideoCaptureSource::processNewFrame):
(WebCore::AVVideoCaptureSource::createPreview):
(WebCore::AVVideoCaptureSource::platformLayer): Deleted.
* platform/mediastream/mac/MockRealtimeVideoSourceMac.h:
* platform/mediastream/mac/MockRealtimeVideoSourceMac.mm:
(WebCore::MockRealtimeVideoSourceMac::platformLayer): Deleted.
(WebCore::MockRealtimeVideoSourceMac::updatePlatformLayer): Deleted.
* platform/mock/MockRealtimeVideoSource.cpp:
(WebCore::MockRealtimeVideoSource::applyFrameRate):
(WebCore::MockRealtimeVideoSource::applySize):
(WebCore::MockRealtimeVideoSource::generateFrame):
* platform/mock/MockRealtimeVideoSource.h:
(WebCore::MockRealtimeVideoSource::updatePlatformLayer): Deleted.</pre>
<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreWebCorexcodeprojprojectpbxproj">trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceWebCorehtmlHTMLMediaElementcpp">trunk/Source/WebCore/html/HTMLMediaElement.cpp</a></li>
<li><a href="#trunkSourceWebCorehtmlHTMLMediaElementh">trunk/Source/WebCore/html/HTMLMediaElement.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsavfoundationobjcMediaPlayerPrivateMediaStreamAVFObjCh">trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsavfoundationobjcMediaPlayerPrivateMediaStreamAVFObjCmm">trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.mm</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamMediaStreamPrivatecpp">trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamMediaStreamPrivateh">trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamMediaStreamTrackPrivatecpp">trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamMediaStreamTrackPrivateh">trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceh">trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVAudioCaptureSourceh">trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVAudioCaptureSourcemm">trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.mm</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVMediaCaptureSourceh">trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVMediaCaptureSourcemm">trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.mm</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVVideoCaptureSourceh">trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVVideoCaptureSourcemm">trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.mm</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacMockRealtimeVideoSourceMach">trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacMockRealtimeVideoSourceMacmm">trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.mm</a></li>
<li><a href="#trunkSourceWebCoreplatformmockMockRealtimeVideoSourcecpp">trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmockMockRealtimeVideoSourceh">trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.h</a></li>
</ul>
<h3>Added Paths</h3>
<ul>
<li><a href="#trunkSourceWebCoreplatformmediastreamRealtimeMediaSourcePreviewh">trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourcePreview.h</a></li>
</ul>
</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/ChangeLog        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -1,3 +1,109 @@
</span><ins>+2016-11-17 Eric Carlson <eric.carlson@apple.com>
+
+ [MediaStream][Mac] Use AVCapturePreview object for camera/microphone rendering
+ https://bugs.webkit.org/show_bug.cgi?id=164837
+ <rdar://problem/29297727>
+
+ Reviewed by Jer Noble.
+
+ No new tests, the real capture devices can not be used in layout tests.
+
+ * WebCore.xcodeproj/project.pbxproj:
+
+ Drive-by fix: clear m_settingMediaStreamSrcObject when the media player is destroyed unless
+ that happens as a side effect of setting video.srcObject.
+ * html/HTMLMediaElement.cpp:
+ (WebCore::HTMLMediaElement::setSrcObject):
+ (WebCore::HTMLMediaElement::clearMediaPlayer):
+ * html/HTMLMediaElement.h:
+
+ Add support for realtime media source that vend a preview interface, while keeping support
+ for those that do not (e.g. the mock capture devices).
+ * platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.h:
+ * platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.mm:
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::MediaPlayerPrivateMediaStreamAVFObjC):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::isAvailable):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::enqueueVideoSampleBuffer):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::prepareVideoSampleBufferFromTrack):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::ensureLayer):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::destroyLayer):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::platformLayer):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::currentDisplayMode):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::play):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::pause):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::internalSetVolume):
+ (WebCore::MediaPlayerPrivateMediaStreamAVFObjC::updateTracks):
+
+ * platform/mediastream/MediaStreamPrivate.cpp:
+ (WebCore::MediaStreamPrivate::platformLayer): Deleted, no longer used.
+ * platform/mediastream/MediaStreamPrivate.h:
+
+ Enable/disable the preview when available.
+ * platform/mediastream/MediaStreamTrackPrivate.cpp:
+ (WebCore::MediaStreamTrackPrivate::setEnabled):
+ (WebCore::MediaStreamTrackPrivate::endTrack):
+ (WebCore::MediaStreamTrackPrivate::preview):
+ * platform/mediastream/MediaStreamTrackPrivate.h:
+
+ * platform/mediastream/RealtimeMediaSource.h:
+ (WebCore::RealtimeMediaSource::preview):
+ (WebCore::RealtimeMediaSource::createWeakPtr):
+ (WebCore::RealtimeMediaSource::platformLayer): Deleted.
+
+ Define a realtime media source preview interface.
+ * platform/mediastream/RealtimeMediaSourcePreview.h: Added.
+ (WebCore::RealtimeMediaSourcePreview::~RealtimeMediaSourcePreview):
+ (WebCore::RealtimeMediaSourcePreview::invalidate):
+ (WebCore::RealtimeMediaSourcePreview::createWeakPtr):
+ (WebCore::RealtimeMediaSourcePreview::RealtimeMediaSourcePreview):
+
+ Implement the preview interface.
+ * platform/mediastream/mac/AVAudioCaptureSource.h:
+ * platform/mediastream/mac/AVAudioCaptureSource.mm:
+ (WebCore::AVAudioSourcePreview::create):
+ (WebCore::AVAudioSourcePreview::AVAudioSourcePreview):
+ (WebCore::AVAudioSourcePreview::invalidate):
+ (WebCore::AVAudioSourcePreview::play):
+ (WebCore::AVAudioSourcePreview::pause):
+ (WebCore::AVAudioSourcePreview::setEnabled):
+ (WebCore::AVAudioSourcePreview::setVolume):
+ (WebCore::AVAudioSourcePreview::updateState):
+ (WebCore::AVAudioCaptureSource::createPreview):
+ * platform/mediastream/mac/AVMediaCaptureSource.h:
+ (WebCore::AVMediaCaptureSource::createWeakPtr):
+ * platform/mediastream/mac/AVMediaCaptureSource.mm:
+ (WebCore::AVMediaCaptureSource::AVMediaCaptureSource):
+ (WebCore::AVMediaCaptureSource::reset):
+ (WebCore::AVMediaCaptureSource::preview):
+ (WebCore::AVMediaCaptureSource::removePreview):
+ (WebCore::AVMediaSourcePreview::AVMediaSourcePreview):
+ (WebCore::AVMediaSourcePreview::~AVMediaSourcePreview):
+ (WebCore::AVMediaSourcePreview::invalidate):
+ * platform/mediastream/mac/AVVideoCaptureSource.h:
+ * platform/mediastream/mac/AVVideoCaptureSource.mm:
+ (WebCore::AVVideoSourcePreview::create):
+ (WebCore::AVVideoSourcePreview::AVVideoSourcePreview):
+ (WebCore::AVVideoSourcePreview::invalidate):
+ (WebCore::AVVideoSourcePreview::play):
+ (WebCore::AVVideoSourcePreview::pause):
+ (WebCore::AVVideoSourcePreview::setPaused):
+ (WebCore::AVVideoSourcePreview::setEnabled):
+ (WebCore::AVVideoCaptureSource::shutdownCaptureSession):
+ (WebCore::AVVideoCaptureSource::processNewFrame):
+ (WebCore::AVVideoCaptureSource::createPreview):
+ (WebCore::AVVideoCaptureSource::platformLayer): Deleted.
+
+ * platform/mediastream/mac/MockRealtimeVideoSourceMac.h:
+ * platform/mediastream/mac/MockRealtimeVideoSourceMac.mm:
+ (WebCore::MockRealtimeVideoSourceMac::platformLayer): Deleted.
+ (WebCore::MockRealtimeVideoSourceMac::updatePlatformLayer): Deleted.
+ * platform/mock/MockRealtimeVideoSource.cpp:
+ (WebCore::MockRealtimeVideoSource::applyFrameRate):
+ (WebCore::MockRealtimeVideoSource::applySize):
+ (WebCore::MockRealtimeVideoSource::generateFrame):
+ * platform/mock/MockRealtimeVideoSource.h:
+ (WebCore::MockRealtimeVideoSource::updatePlatformLayer): Deleted.
+
</ins><span class="cx"> 2016-11-17 Chris Dumez <cdumez@apple.com>
</span><span class="cx">
</span><span class="cx"> Unreviewed, fix build after r208839.
</span></span></pre></div>
<a id="trunkSourceWebCoreWebCorexcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -305,6 +305,7 @@
</span><span class="cx">                 07C59B6917F784BA000FBCBB /* MediaSourceSettings.h in Headers */ = {isa = PBXBuildFile; fileRef = 07C59B6617F784BA000FBCBB /* MediaSourceSettings.h */; };
</span><span class="cx">                 07C59B6E17F794F6000FBCBB /* JSMediaStreamTrackCustom.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 07C59B6D17F794F6000FBCBB /* JSMediaStreamTrackCustom.cpp */; };
</span><span class="cx">                 07CE77D516712A6A00C55A47 /* InbandTextTrackPrivateClient.h in Headers */ = {isa = PBXBuildFile; fileRef = 07CE77D416712A6A00C55A47 /* InbandTextTrackPrivateClient.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><ins>+                07D1503B1DDB6965008F7598 /* RealtimeMediaSourcePreview.h in Headers */ = {isa = PBXBuildFile; fileRef = 07D1503A1DDB6688008F7598 /* RealtimeMediaSourcePreview.h */; settings = {ATTRIBUTES = (Private, ); }; };
</ins><span class="cx">                 07D637401BB0B11300256CE9 /* WebAudioSourceProviderAVFObjC.h in Headers */ = {isa = PBXBuildFile; fileRef = 07D6373E1BB0B11300256CE9 /* WebAudioSourceProviderAVFObjC.h */; };
</span><span class="cx">                 07D637411BB0B11300256CE9 /* WebAudioSourceProviderAVFObjC.mm in Sources */ = {isa = PBXBuildFile; fileRef = 07D6373F1BB0B11300256CE9 /* WebAudioSourceProviderAVFObjC.mm */; };
</span><span class="cx">                 07D6A4EF1BECF2D200174146 /* MockRealtimeMediaSource.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 07D6A4ED1BECF2D200174146 /* MockRealtimeMediaSource.cpp */; };
</span><span class="lines">@@ -7262,6 +7263,7 @@
</span><span class="cx">                 07C8AD111D073D630087C5CE /* AVFoundationMIMETypeCache.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = AVFoundationMIMETypeCache.mm; sourceTree = "<group>"; };
</span><span class="cx">                 07C8AD121D073D630087C5CE /* AVFoundationMIMETypeCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AVFoundationMIMETypeCache.h; sourceTree = "<group>"; };
</span><span class="cx">                 07CE77D416712A6A00C55A47 /* InbandTextTrackPrivateClient.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = InbandTextTrackPrivateClient.h; sourceTree = "<group>"; };
</span><ins>+                07D1503A1DDB6688008F7598 /* RealtimeMediaSourcePreview.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RealtimeMediaSourcePreview.h; sourceTree = "<group>"; };
</ins><span class="cx">                 07D6373E1BB0B11300256CE9 /* WebAudioSourceProviderAVFObjC.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WebAudioSourceProviderAVFObjC.h; sourceTree = "<group>"; };
</span><span class="cx">                 07D6373F1BB0B11300256CE9 /* WebAudioSourceProviderAVFObjC.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = WebAudioSourceProviderAVFObjC.mm; sourceTree = "<group>"; };
</span><span class="cx">                 07D6A4ED1BECF2D200174146 /* MockRealtimeMediaSource.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MockRealtimeMediaSource.cpp; sourceTree = "<group>"; };
</span><span class="lines">@@ -15104,6 +15106,7 @@
</span><span class="cx">                 07221B9217CF0AD400848E51 /* mediastream */ = {
</span><span class="cx">                         isa = PBXGroup;
</span><span class="cx">                         children = (
</span><ins>+                                07D1503A1DDB6688008F7598 /* RealtimeMediaSourcePreview.h */,
</ins><span class="cx">                                 0729B14D17CFCCA0004F1D60 /* mac */,
</span><span class="cx">                                 07D6A4F61BF2307D00174146 /* AudioTrackPrivateMediaStream.h */,
</span><span class="cx">                                 07B7116A1D899E63009F0FFB /* CaptureDevice.h */,
</span><span class="lines">@@ -28149,6 +28152,7 @@
</span><span class="cx">                                 1411DCB1164C39A800D49BC1 /* WidthCache.h in Headers */,
</span><span class="cx">                                 939B02EF0EA2DBC400C54570 /* WidthIterator.h in Headers */,
</span><span class="cx">                                 0F15ED5C1B7EC7C500EDDFEB /* WillChangeData.h in Headers */,
</span><ins>+                                07D1503B1DDB6965008F7598 /* RealtimeMediaSourcePreview.h in Headers */,
</ins><span class="cx">                                 BC8243E90D0CFD7500460C8F /* WindowFeatures.h in Headers */,
</span><span class="cx">                                 7E99AF530B13846468FB01A5 /* WindowFocusAllowedIndicator.h in Headers */,
</span><span class="cx">                                 E1E1BF00115FF6FB006F52CA /* WindowsKeyboardCodes.h in Headers */,
</span></span></pre></div>
<a id="trunkSourceWebCorehtmlHTMLMediaElementcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/html/HTMLMediaElement.cpp (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/html/HTMLMediaElement.cpp        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/html/HTMLMediaElement.cpp        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -1048,8 +1048,11 @@
</span><span class="cx"> // https://bugs.webkit.org/show_bug.cgi?id=124896
</span><span class="cx">
</span><span class="cx"> m_mediaStreamSrcObject = mediaStream;
</span><del>- if (mediaStream)
</del><ins>+ if (mediaStream) {
+ m_settingMediaStreamSrcObject = true;
</ins><span class="cx"> setSrc(DOMURL::createPublicURL(context, *mediaStream));
</span><ins>+ m_settingMediaStreamSrcObject = false;
+ }
</ins><span class="cx"> }
</span><span class="cx"> #endif
</span><span class="cx">
</span><span class="lines">@@ -4983,6 +4986,11 @@
</span><span class="cx"> {
</span><span class="cx"> LOG(Media, "HTMLMediaElement::clearMediaPlayer(%p) - flags = %s", this, actionName(flags).utf8().data());
</span><span class="cx">
</span><ins>+#if ENABLE(MEDIA_STREAM)
+ if (!m_settingMediaStreamSrcObject)
+ m_mediaStreamSrcObject = nullptr;
+#endif
+
</ins><span class="cx"> #if ENABLE(MEDIA_SOURCE)
</span><span class="cx"> detachMediaSource();
</span><span class="cx"> #endif
</span></span></pre></div>
<a id="trunkSourceWebCorehtmlHTMLMediaElementh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/html/HTMLMediaElement.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/html/HTMLMediaElement.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/html/HTMLMediaElement.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -1023,6 +1023,7 @@
</span><span class="cx">
</span><span class="cx"> #if ENABLE(MEDIA_STREAM)
</span><span class="cx"> RefPtr<MediaStream> m_mediaStreamSrcObject;
</span><ins>+ bool m_settingMediaStreamSrcObject { false };
</ins><span class="cx"> #endif
</span><span class="cx">
</span><span class="cx"> #if ENABLE(WIRELESS_PLAYBACK_TARGET)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsavfoundationobjcMediaPlayerPrivateMediaStreamAVFObjCh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -186,11 +186,19 @@
</span><span class="cx"> void setVideoFullscreenFrame(FloatRect) override;
</span><span class="cx"> #endif
</span><span class="cx">
</span><ins>+ bool haveVideoLayer() const { return m_sampleBufferDisplayLayer || m_videoPreviewPlayer; }
+
</ins><span class="cx"> MediaPlayer* m_player { nullptr };
</span><span class="cx"> WeakPtrFactory<MediaPlayerPrivateMediaStreamAVFObjC> m_weakPtrFactory;
</span><span class="cx"> RefPtr<MediaStreamPrivate> m_mediaStreamPrivate;
</span><ins>+
+ RefPtr<RealtimeMediaSourcePreview> m_videoPreviewPlayer;
+ RefPtr<MediaStreamTrackPrivate> m_videoTrack;
+
</ins><span class="cx"> RetainPtr<AVSampleBufferDisplayLayer> m_sampleBufferDisplayLayer;
</span><ins>+#if PLATFORM(MAC)
</ins><span class="cx"> RetainPtr<AVSampleBufferRenderSynchronizer> m_synchronizer;
</span><ins>+#endif
</ins><span class="cx"> RetainPtr<CGImageRef> m_pausedImage;
</span><span class="cx"> double m_pausedTime { 0 };
</span><span class="cx"> std::unique_ptr<Clock> m_clock;
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsavfoundationobjcMediaPlayerPrivateMediaStreamAVFObjCmm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.mm (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.mm        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/graphics/avfoundation/objc/MediaPlayerPrivateMediaStreamAVFObjC.mm        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -28,9 +28,7 @@
</span><span class="cx">
</span><span class="cx"> #if ENABLE(MEDIA_STREAM) && USE(AVFOUNDATION)
</span><span class="cx">
</span><del>-#import "AVAudioCaptureSource.h"
</del><span class="cx"> #import "AVFoundationSPI.h"
</span><del>-#import "AVVideoCaptureSource.h"
</del><span class="cx"> #import "AudioTrackPrivateMediaStream.h"
</span><span class="cx"> #import "Clock.h"
</span><span class="cx"> #import "GraphicsContext.h"
</span><span class="lines">@@ -66,7 +64,6 @@
</span><span class="cx"> MediaPlayerPrivateMediaStreamAVFObjC::MediaPlayerPrivateMediaStreamAVFObjC(MediaPlayer* player)
</span><span class="cx"> : m_player(player)
</span><span class="cx"> , m_weakPtrFactory(this)
</span><del>- , m_synchronizer(adoptNS([allocAVSampleBufferRenderSynchronizerInstance() init]))
</del><span class="cx"> , m_clock(Clock::create())
</span><span class="cx"> #if PLATFORM(MAC) && ENABLE(VIDEO_PRESENTATION_MODE)
</span><span class="cx"> , m_videoFullscreenLayerManager(VideoFullscreenLayerManager::create())
</span><span class="lines">@@ -103,7 +100,15 @@
</span><span class="cx">
</span><span class="cx"> bool MediaPlayerPrivateMediaStreamAVFObjC::isAvailable()
</span><span class="cx"> {
</span><del>- return AVFoundationLibrary() && isCoreMediaFrameworkAvailable() && getAVSampleBufferDisplayLayerClass() && getAVSampleBufferRenderSynchronizerClass();
</del><ins>+ if (!AVFoundationLibrary() || !isCoreMediaFrameworkAvailable() || !getAVSampleBufferDisplayLayerClass())
+ return false;
+
+#if PLATFORM(MAC)
+ if (!getAVSampleBufferRenderSynchronizerClass())
+ return false;
+#endif
+
+ return true;
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> void MediaPlayerPrivateMediaStreamAVFObjC::getSupportedTypes(HashSet<String, ASCIICaseInsensitiveHash>& types)
</span><span class="lines">@@ -147,11 +152,17 @@
</span><span class="cx">
</span><span class="cx"> void MediaPlayerPrivateMediaStreamAVFObjC::enqueueVideoSampleBuffer(MediaSample& sample)
</span><span class="cx"> {
</span><del>- ASSERT([m_sampleBufferDisplayLayer isReadyForMoreMediaData]);
</del><ins>+ if (m_sampleBufferDisplayLayer) {
+ if (![m_sampleBufferDisplayLayer isReadyForMoreMediaData]) {
+ m_sampleQueue.append(sample);
+ requestNotificationWhenReadyForMediaData();
+ return;
+ }
</ins><span class="cx">
</span><del>- [m_sampleBufferDisplayLayer enqueueSampleBuffer:sample.platformSample().sample.cmSampleBuffer];
</del><ins>+ [m_sampleBufferDisplayLayer enqueueSampleBuffer:sample.platformSample().sample.cmSampleBuffer];
+ }
+
</ins><span class="cx"> m_isFrameDisplayed = true;
</span><del>-
</del><span class="cx"> if (!m_hasEverEnqueuedVideoFrame) {
</span><span class="cx"> m_hasEverEnqueuedVideoFrame = true;
</span><span class="cx"> m_player->firstVideoFrameAvailable();
</span><span class="lines">@@ -164,12 +175,6 @@
</span><span class="cx"> if (&track != m_mediaStreamPrivate->activeVideoTrack() || !shouldEnqueueVideoSampleBuffer())
</span><span class="cx"> return;
</span><span class="cx">
</span><del>- if (![m_sampleBufferDisplayLayer isReadyForMoreMediaData]) {
- m_sampleQueue.append(sample);
- requestNotificationWhenReadyForMediaData();
- return;
- }
-
</del><span class="cx"> enqueueVideoSampleBuffer(sample);
</span><span class="cx"> }
</span><span class="cx">
</span><span class="lines">@@ -192,37 +197,56 @@
</span><span class="cx">
</span><span class="cx"> void MediaPlayerPrivateMediaStreamAVFObjC::ensureLayer()
</span><span class="cx"> {
</span><del>- if (m_sampleBufferDisplayLayer)
</del><ins>+ if (haveVideoLayer())
</ins><span class="cx"> return;
</span><del>-
- m_sampleBufferDisplayLayer = adoptNS([allocAVSampleBufferDisplayLayerInstance() init]);
</del><ins>+
+ CALayer *videoLayer = nil;
+ if (m_mediaStreamPrivate->activeVideoTrack()) {
+ m_videoPreviewPlayer = m_mediaStreamPrivate->activeVideoTrack()->preview();
+ if (m_videoPreviewPlayer)
+ videoLayer = m_videoPreviewPlayer->platformLayer();
+ }
+
+ if (!videoLayer) {
+ m_sampleBufferDisplayLayer = adoptNS([allocAVSampleBufferDisplayLayerInstance() init]);
+ videoLayer = m_sampleBufferDisplayLayer.get();
</ins><span class="cx"> #ifndef NDEBUG
</span><del>- [m_sampleBufferDisplayLayer setName:@"MediaPlayerPrivateMediaStreamAVFObjC AVSampleBufferDisplayLayer"];
</del><ins>+ [m_sampleBufferDisplayLayer setName:@"MediaPlayerPrivateMediaStreamAVFObjC AVSampleBufferDisplayLayer"];
</ins><span class="cx"> #endif
</span><del>- m_sampleBufferDisplayLayer.get().backgroundColor = cachedCGColor(Color::black);
</del><ins>+ m_sampleBufferDisplayLayer.get().backgroundColor = cachedCGColor(Color::black);
</ins><span class="cx">
</span><del>- [m_synchronizer addRenderer:m_sampleBufferDisplayLayer.get()];
</del><ins>+#if PLATFORM(MAC)
+ m_synchronizer = adoptNS([allocAVSampleBufferRenderSynchronizerInstance() init]);
+ [m_synchronizer addRenderer:m_sampleBufferDisplayLayer.get()];
+#endif
+ }
</ins><span class="cx">
</span><span class="cx"> renderingModeChanged();
</span><span class="cx">
</span><span class="cx"> #if PLATFORM(MAC) && ENABLE(VIDEO_PRESENTATION_MODE)
</span><del>- m_videoFullscreenLayerManager->setVideoLayer(m_sampleBufferDisplayLayer.get(), snappedIntRect(m_player->client().mediaPlayerContentBoxRect()).size());
</del><ins>+ m_videoFullscreenLayerManager->setVideoLayer(videoLayer, snappedIntRect(m_player->client().mediaPlayerContentBoxRect()).size());
</ins><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> void MediaPlayerPrivateMediaStreamAVFObjC::destroyLayer()
</span><span class="cx"> {
</span><del>- if (!m_sampleBufferDisplayLayer)
</del><ins>+ if (!haveVideoLayer())
</ins><span class="cx"> return;
</span><del>-
- [m_sampleBufferDisplayLayer stopRequestingMediaData];
- [m_sampleBufferDisplayLayer flush];
- CMTime currentTime = CMTimebaseGetTime([m_synchronizer timebase]);
- [m_synchronizer removeRenderer:m_sampleBufferDisplayLayer.get() atTime:currentTime withCompletionHandler:^(BOOL){
- // No-op.
- }];
- m_sampleBufferDisplayLayer = nullptr;
</del><span class="cx">
</span><ins>+ m_videoPreviewPlayer = nullptr;
+
+ if (m_sampleBufferDisplayLayer) {
+ [m_sampleBufferDisplayLayer stopRequestingMediaData];
+ [m_sampleBufferDisplayLayer flush];
+#if PLATFORM(MAC)
+ CMTime currentTime = CMTimebaseGetTime([m_synchronizer timebase]);
+ [m_synchronizer removeRenderer:m_sampleBufferDisplayLayer.get() atTime:currentTime withCompletionHandler:^(BOOL) {
+ // No-op.
+ }];
+ m_sampleBufferDisplayLayer = nullptr;
+#endif
+ }
+
</ins><span class="cx"> renderingModeChanged();
</span><span class="cx">
</span><span class="cx"> #if PLATFORM(MAC) && ENABLE(VIDEO_PRESENTATION_MODE)
</span><span class="lines">@@ -282,12 +306,15 @@
</span><span class="cx">
</span><span class="cx"> PlatformLayer* MediaPlayerPrivateMediaStreamAVFObjC::platformLayer() const
</span><span class="cx"> {
</span><del>- if (!m_sampleBufferDisplayLayer || m_displayMode == None)
</del><ins>+ if (!haveVideoLayer() || m_displayMode == None)
</ins><span class="cx"> return nullptr;
</span><span class="cx">
</span><span class="cx"> #if PLATFORM(MAC) && ENABLE(VIDEO_PRESENTATION_MODE)
</span><span class="cx"> return m_videoFullscreenLayerManager->videoInlineLayer();
</span><span class="cx"> #else
</span><ins>+ if (m_videoPreviewPlayer)
+ return m_videoPreviewPlayer->platformLayer();
+
</ins><span class="cx"> return m_sampleBufferDisplayLayer.get();
</span><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="lines">@@ -294,7 +321,7 @@
</span><span class="cx">
</span><span class="cx"> MediaPlayerPrivateMediaStreamAVFObjC::DisplayMode MediaPlayerPrivateMediaStreamAVFObjC::currentDisplayMode() const
</span><span class="cx"> {
</span><del>- if (m_ended || m_intrinsicSize.isEmpty() || !metaDataAvailable() || !m_sampleBufferDisplayLayer)
</del><ins>+ if (m_ended || m_intrinsicSize.isEmpty() || !metaDataAvailable() || !haveVideoLayer())
</ins><span class="cx"> return None;
</span><span class="cx">
</span><span class="cx"> if (m_mediaStreamPrivate->activeVideoTrack() && !m_mediaStreamPrivate->activeVideoTrack()->enabled())
</span><span class="lines">@@ -344,7 +371,21 @@
</span><span class="cx">
</span><span class="cx"> m_clock->start();
</span><span class="cx"> m_playing = true;
</span><del>- [m_synchronizer setRate:1];
</del><ins>+
+ if (m_videoPreviewPlayer)
+ m_videoPreviewPlayer->play();
+#if PLATFORM(MAC)
+ else
+ [m_synchronizer setRate:1];
+#endif
+
+ for (const auto& track : m_audioTrackMap.values()) {
+ if (!track->enabled() || !track->streamTrack()->preview())
+ continue;
+
+ track->streamTrack()->preview()->play();
+ }
+
</ins><span class="cx"> m_haveEverPlayed = true;
</span><span class="cx"> scheduleDeferredTask([this] {
</span><span class="cx"> updateDisplayMode();
</span><span class="lines">@@ -361,7 +402,21 @@
</span><span class="cx">
</span><span class="cx"> m_pausedTime = m_clock->currentTime();
</span><span class="cx"> m_playing = false;
</span><del>- [m_synchronizer setRate:0];
</del><ins>+
+ if (m_videoPreviewPlayer)
+ m_videoPreviewPlayer->pause();
+#if PLATFORM(MAC)
+ else
+ [m_synchronizer setRate:0];
+#endif
+
+ for (const auto& track : m_audioTrackMap.values()) {
+ if (!track->enabled() || !track->streamTrack()->preview())
+ continue;
+
+ track->streamTrack()->preview()->pause();
+ }
+
</ins><span class="cx"> updateDisplayMode();
</span><span class="cx"> updatePausedImage();
</span><span class="cx"> }
</span><span class="lines">@@ -379,7 +434,12 @@
</span><span class="cx"> if (!metaDataAvailable())
</span><span class="cx"> return;
</span><span class="cx">
</span><del>- // FIXME: Set volume once we actually play audio.
</del><ins>+ for (const auto& track : m_audioTrackMap.values()) {
+ if (!track->enabled() || !track->streamTrack()->preview())
+ continue;
+
+ track->streamTrack()->preview()->setVolume(volume);
+ }
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> void MediaPlayerPrivateMediaStreamAVFObjC::setVolume(float volume)
</span><span class="lines">@@ -627,9 +687,10 @@
</span><span class="cx"> std::function<void(RefPtr<VideoTrackPrivateMediaStream>, int)> enableVideoTrack = [this](auto track, int index)
</span><span class="cx"> {
</span><span class="cx"> track->setTrackIndex(index);
</span><del>- track->setSelected(track->streamTrack() == m_mediaStreamPrivate->activeVideoTrack());
</del><ins>+ bool selected = track->streamTrack() == m_mediaStreamPrivate->activeVideoTrack();
+ track->setSelected(selected);
</ins><span class="cx">
</span><del>- if (track->selected())
</del><ins>+ if (selected)
</ins><span class="cx"> ensureLayer();
</span><span class="cx"> };
</span><span class="cx"> updateTracksOfType(m_videoTrackMap, RealtimeMediaSource::Video, currentTracks, &VideoTrackPrivateMediaStream::create, m_player, &MediaPlayer::removeVideoTrack, &MediaPlayer::addVideoTrack, enableVideoTrack, (MediaStreamTrackPrivate::Observer*) this);
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamMediaStreamPrivatecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.cpp (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.cpp        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.cpp        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -239,14 +239,6 @@
</span><span class="cx"> return size;
</span><span class="cx"> }
</span><span class="cx">
</span><del>-PlatformLayer* MediaStreamPrivate::platformLayer() const
-{
- if (!m_activeVideoTrack)
- return nullptr;
-
- return m_activeVideoTrack->source().platformLayer();
-}
-
</del><span class="cx"> void MediaStreamPrivate::paintCurrentFrameInContext(GraphicsContext& context, const FloatRect& rect)
</span><span class="cx"> {
</span><span class="cx"> if (context.paintingDisabled())
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamMediaStreamPrivateh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/MediaStreamPrivate.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -93,7 +93,6 @@
</span><span class="cx"> void stopProducingData();
</span><span class="cx"> bool isProducingData() const;
</span><span class="cx">
</span><del>- PlatformLayer* platformLayer() const;
</del><span class="cx"> RefPtr<Image> currentFrameImage();
</span><span class="cx"> void paintCurrentFrameInContext(GraphicsContext&, const FloatRect&);
</span><span class="cx">
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamMediaStreamTrackPrivatecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.cpp (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.cpp        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.cpp        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -101,6 +101,9 @@
</span><span class="cx"> // Always update the enabled state regardless of the track being ended.
</span><span class="cx"> m_isEnabled = enabled;
</span><span class="cx">
</span><ins>+ if (m_preview)
+ m_preview->setEnabled(enabled);
+
</ins><span class="cx"> for (auto& observer : m_observers)
</span><span class="cx"> observer->trackEnabledChanged(*this);
</span><span class="cx"> }
</span><span class="lines">@@ -115,6 +118,7 @@
</span><span class="cx"> // trackEnded method once.
</span><span class="cx"> m_isEnded = true;
</span><span class="cx">
</span><ins>+ m_preview = nullptr;
</ins><span class="cx"> m_source->requestStop(this);
</span><span class="cx">
</span><span class="cx"> for (auto& observer : m_observers)
</span><span class="lines">@@ -166,6 +170,15 @@
</span><span class="cx"> }
</span><span class="cx"> }
</span><span class="cx">
</span><ins>+RealtimeMediaSourcePreview* MediaStreamTrackPrivate::preview()
+{
+ if (m_preview)
+ return m_preview.get();
+
+ m_preview = m_source->preview();
+ return m_preview.get();
+}
+
</ins><span class="cx"> void MediaStreamTrackPrivate::applyConstraints(const MediaConstraints& constraints, RealtimeMediaSource::SuccessHandler successHandler, RealtimeMediaSource::FailureHandler failureHandler)
</span><span class="cx"> {
</span><span class="cx"> m_source->applyConstraints(constraints, successHandler, failureHandler);
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamMediaStreamTrackPrivateh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/MediaStreamTrackPrivate.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -96,6 +96,7 @@
</span><span class="cx"> AudioSourceProvider* audioSourceProvider();
</span><span class="cx">
</span><span class="cx"> void paintCurrentFrameInContext(GraphicsContext&, const FloatRect&);
</span><ins>+ RealtimeMediaSourcePreview* preview();
</ins><span class="cx">
</span><span class="cx"> private:
</span><span class="cx"> MediaStreamTrackPrivate(Ref<RealtimeMediaSource>&&, String&& id);
</span><span class="lines">@@ -110,6 +111,7 @@
</span><span class="cx"> Vector<Observer*> m_observers;
</span><span class="cx"> Ref<RealtimeMediaSource> m_source;
</span><span class="cx"> RefPtr<MediaConstraints> m_constraints;
</span><ins>+ RefPtr<RealtimeMediaSourcePreview> m_preview;
</ins><span class="cx">
</span><span class="cx"> String m_id;
</span><span class="cx"> bool m_isEnabled;
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -42,6 +42,7 @@
</span><span class="cx"> #include "MediaSample.h"
</span><span class="cx"> #include "PlatformLayer.h"
</span><span class="cx"> #include "RealtimeMediaSourceCapabilities.h"
</span><ins>+#include "RealtimeMediaSourcePreview.h"
</ins><span class="cx"> #include <wtf/RefCounted.h>
</span><span class="cx"> #include <wtf/Vector.h>
</span><span class="cx"> #include <wtf/WeakPtr.h>
</span><span class="lines">@@ -126,9 +127,9 @@
</span><span class="cx">
</span><span class="cx"> virtual AudioSourceProvider* audioSourceProvider() { return nullptr; }
</span><span class="cx">
</span><del>- virtual PlatformLayer* platformLayer() const { return nullptr; }
</del><span class="cx"> virtual RefPtr<Image> currentFrameImage() { return nullptr; }
</span><span class="cx"> virtual void paintCurrentFrameInContext(GraphicsContext&, const FloatRect&) { }
</span><ins>+ virtual RefPtr<RealtimeMediaSourcePreview> preview() { return nullptr; }
</ins><span class="cx">
</span><span class="cx"> void setWidth(int);
</span><span class="cx"> void setHeight(int);
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamRealtimeMediaSourcePreviewhfromrev208850trunkSourceWebCoreplatformmediastreammacMockRealtimeVideoSourceMach"></a>
<div class="copfile"><h4>Copied: trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourcePreview.h (from rev 208850, trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.h) (0 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourcePreview.h         (rev 0)
+++ trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourcePreview.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -0,0 +1,69 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ * 3. Neither the name of Ericsson nor the names of its contributors
+ * may be used to endorse or promote products derived from this
+ * software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#pragma once
+
+#if ENABLE(MEDIA_STREAM)
+
+#include "PlatformLayer.h"
+#include <wtf/RetainPtr.h>
+#include <wtf/WeakPtr.h>
+
+namespace WebCore {
+
+class RealtimeMediaSourcePreview : public RefCounted<RealtimeMediaSourcePreview> {
+public:
+ virtual ~RealtimeMediaSourcePreview() { }
+
+ virtual void play() const = 0;
+ virtual void pause() const = 0;
+ virtual void setEnabled(bool) = 0;
+
+ virtual PlatformLayer* platformLayer() const = 0;
+ virtual void setVolume(double) const = 0;
+
+ virtual void invalidate() { m_weakPtrFactory.revokeAll(); }
+
+ WeakPtr<RealtimeMediaSourcePreview> createWeakPtr() { return m_weakPtrFactory.createWeakPtr(); }
+
+protected:
+ RealtimeMediaSourcePreview()
+ : m_weakPtrFactory(this)
+ {
+ }
+
+private:
+ WeakPtrFactory<RealtimeMediaSourcePreview> m_weakPtrFactory;
+};
+
+} // namespace WebCore
+
+#endif // ENABLE(MEDIA_STREAM)
+
</ins></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVAudioCaptureSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -67,6 +67,7 @@
</span><span class="cx"> void shutdownCaptureSession() override;
</span><span class="cx"> void updateSettings(RealtimeMediaSourceSettings&) override;
</span><span class="cx"> AudioSourceProvider* audioSourceProvider() override;
</span><ins>+ RefPtr<AVMediaSourcePreview> createPreview() final;
</ins><span class="cx">
</span><span class="cx"> RetainPtr<AVCaptureConnection> m_audioConnection;
</span><span class="cx">
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVAudioCaptureSourcemm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.mm (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.mm        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.mm        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -47,15 +47,31 @@
</span><span class="cx"> typedef AVCaptureDeviceInput AVCaptureDeviceInputType;
</span><span class="cx"> typedef AVCaptureOutput AVCaptureOutputType;
</span><span class="cx">
</span><ins>+#if !PLATFORM(IOS)
+typedef AVCaptureAudioPreviewOutput AVCaptureAudioPreviewOutputType;
+#endif
+
</ins><span class="cx"> SOFT_LINK_FRAMEWORK_OPTIONAL(AVFoundation)
</span><span class="cx">
</span><span class="cx"> SOFT_LINK_CLASS(AVFoundation, AVCaptureAudioChannel)
</span><span class="cx"> SOFT_LINK_CLASS(AVFoundation, AVCaptureAudioDataOutput)
</span><ins>+SOFT_LINK_CLASS(AVFoundation, AVCaptureAudioPreviewOutput)
</ins><span class="cx"> SOFT_LINK_CLASS(AVFoundation, AVCaptureConnection)
</span><span class="cx"> SOFT_LINK_CLASS(AVFoundation, AVCaptureDevice)
</span><span class="cx"> SOFT_LINK_CLASS(AVFoundation, AVCaptureDeviceInput)
</span><span class="cx"> SOFT_LINK_CLASS(AVFoundation, AVCaptureOutput)
</span><span class="cx">
</span><ins>+#define AVCaptureAudioPreviewOutput getAVCaptureAudioPreviewOutputClass()
+
+#define AVCaptureAudioChannel getAVCaptureAudioChannelClass()
+#define AVCaptureAudioDataOutput getAVCaptureAudioDataOutputClass()
+#define AVCaptureConnection getAVCaptureConnectionClass()
+#define AVCaptureDevice getAVCaptureDeviceClass()
+#define AVCaptureDeviceFormat getAVCaptureDeviceFormatClass()
+#define AVCaptureDeviceInput getAVCaptureDeviceInputClass()
+#define AVCaptureOutput getAVCaptureOutputClass()
+#define AVFrameRateRange getAVFrameRateRangeClass()
+
</ins><span class="cx"> SOFT_LINK_POINTER(AVFoundation, AVMediaTypeAudio, NSString *)
</span><span class="cx">
</span><span class="cx"> #define AVMediaTypeAudio getAVMediaTypeAudio()
</span><span class="lines">@@ -62,6 +78,79 @@
</span><span class="cx">
</span><span class="cx"> namespace WebCore {
</span><span class="cx">
</span><ins>+#if !PLATFORM(IOS)
+class AVAudioSourcePreview: public AVMediaSourcePreview {
+public:
+ static RefPtr<AVMediaSourcePreview> create(AVCaptureSession *, AVAudioCaptureSource*);
+
+private:
+ AVAudioSourcePreview(AVCaptureSession *, AVAudioCaptureSource*);
+
+ void invalidate() final;
+
+ void play() const final;
+ void pause() const final;
+ void setVolume(double) const final;
+ void setEnabled(bool) final;
+ PlatformLayer* platformLayer() const final { return nullptr; }
+
+ void updateState() const;
+
+ RetainPtr<AVCaptureAudioPreviewOutputType> m_audioPreviewOutput;
+ mutable double m_volume { 1 };
+ mutable bool m_paused { false };
+ mutable bool m_enabled { true };
+};
+
+RefPtr<AVMediaSourcePreview> AVAudioSourcePreview::create(AVCaptureSession *session, AVAudioCaptureSource* parent)
+{
+ return adoptRef(new AVAudioSourcePreview(session, parent));
+}
+
+AVAudioSourcePreview::AVAudioSourcePreview(AVCaptureSession *session, AVAudioCaptureSource* parent)
+ : AVMediaSourcePreview(parent)
+{
+ m_audioPreviewOutput = adoptNS([allocAVCaptureAudioPreviewOutputInstance() init]);
+ setVolume(1);
+ [session addOutput:m_audioPreviewOutput.get()];
+}
+
+void AVAudioSourcePreview::invalidate()
+{
+ m_audioPreviewOutput = nullptr;
+ AVMediaSourcePreview::invalidate();
+}
+
+void AVAudioSourcePreview::play() const
+{
+ m_paused = false;
+ updateState();
+}
+
+void AVAudioSourcePreview::pause() const
+{
+ m_paused = true;
+ updateState();
+}
+
+void AVAudioSourcePreview::setEnabled(bool enabled)
+{
+ m_enabled = enabled;
+ updateState();
+}
+
+void AVAudioSourcePreview::setVolume(double volume) const
+{
+ m_volume = volume;
+ m_audioPreviewOutput.get().volume = volume;
+}
+
+void AVAudioSourcePreview::updateState() const
+{
+ m_audioPreviewOutput.get().volume = (!m_enabled || m_paused) ? 0 : m_volume;
+}
+#endif
+
</ins><span class="cx"> RefPtr<AVMediaCaptureSource> AVAudioCaptureSource::create(AVCaptureDeviceTypedef* device, const AtomicString& id, const MediaConstraints* constraints, String& invalidConstraint)
</span><span class="cx"> {
</span><span class="cx"> auto source = adoptRef(new AVAudioCaptureSource(device, id));
</span><span class="lines">@@ -213,6 +302,15 @@
</span><span class="cx"> return m_audioSourceProvider.get();
</span><span class="cx"> }
</span><span class="cx">
</span><ins>+RefPtr<AVMediaSourcePreview> AVAudioCaptureSource::createPreview()
+{
+#if !PLATFORM(IOS)
+ return AVAudioSourcePreview::create(session(), this);
+#else
+ return nullptr;
+#endif
+}
+
</ins><span class="cx"> } // namespace WebCore
</span><span class="cx">
</span><span class="cx"> #endif // ENABLE(MEDIA_STREAM)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVMediaCaptureSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -32,7 +32,6 @@
</span><span class="cx"> #include "RealtimeMediaSource.h"
</span><span class="cx"> #include "Timer.h"
</span><span class="cx"> #include <wtf/Function.h>
</span><del>-#include <wtf/RetainPtr.h>
</del><span class="cx">
</span><span class="cx"> OBJC_CLASS AVCaptureAudioDataOutput;
</span><span class="cx"> OBJC_CLASS AVCaptureConnection;
</span><span class="lines">@@ -46,6 +45,21 @@
</span><span class="cx">
</span><span class="cx"> namespace WebCore {
</span><span class="cx">
</span><ins>+class AVMediaCaptureSource;
+
+class AVMediaSourcePreview: public RealtimeMediaSourcePreview {
+public:
+ virtual ~AVMediaSourcePreview();
+
+ void invalidate() override;
+
+protected:
+ AVMediaSourcePreview(AVMediaCaptureSource*);
+
+private:
+ WeakPtr<AVMediaCaptureSource> m_parent;
+};
+
</ins><span class="cx"> class AVMediaCaptureSource : public RealtimeMediaSource {
</span><span class="cx"> public:
</span><span class="cx"> virtual ~AVMediaCaptureSource();
</span><span class="lines">@@ -62,6 +76,10 @@
</span><span class="cx"> void stopProducingData() final;
</span><span class="cx"> bool isProducingData() const final { return m_isRunning; }
</span><span class="cx">
</span><ins>+ RefPtr<RealtimeMediaSourcePreview> preview() final;
+ void removePreview(AVMediaSourcePreview*);
+ WeakPtr<AVMediaCaptureSource> createWeakPtr() { return m_weakPtrFactory.createWeakPtr(); }
+
</ins><span class="cx"> protected:
</span><span class="cx"> AVMediaCaptureSource(AVCaptureDevice*, const AtomicString&, RealtimeMediaSource::Type);
</span><span class="cx">
</span><span class="lines">@@ -81,6 +99,8 @@
</span><span class="cx"> void setVideoSampleBufferDelegate(AVCaptureVideoDataOutput*);
</span><span class="cx"> void setAudioSampleBufferDelegate(AVCaptureAudioDataOutput*);
</span><span class="cx">
</span><ins>+ virtual RefPtr<AVMediaSourcePreview> createPreview() = 0;
+
</ins><span class="cx"> private:
</span><span class="cx"> void setupSession();
</span><span class="cx"> void reset() final;
</span><span class="lines">@@ -97,6 +117,8 @@
</span><span class="cx"> RefPtr<RealtimeMediaSourceCapabilities> m_capabilities;
</span><span class="cx"> RetainPtr<AVCaptureSession> m_session;
</span><span class="cx"> RetainPtr<AVCaptureDevice> m_device;
</span><ins>+ Vector<WeakPtr<RealtimeMediaSourcePreview>> m_previews;
+ WeakPtrFactory<AVMediaCaptureSource> m_weakPtrFactory;
</ins><span class="cx"> bool m_isRunning { false};
</span><span class="cx"> };
</span><span class="cx">
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVMediaCaptureSourcemm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.mm (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.mm        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.mm        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -126,6 +126,7 @@
</span><span class="cx"> : RealtimeMediaSource(id, type, emptyString())
</span><span class="cx"> , m_objcObserver(adoptNS([[WebCoreAVMediaCaptureSourceObserver alloc] initWithCallback:this]))
</span><span class="cx"> , m_device(device)
</span><ins>+ , m_weakPtrFactory(this)
</ins><span class="cx"> {
</span><span class="cx"> setName(device.localizedName);
</span><span class="cx"> setPersistentID(device.uniqueID);
</span><span class="lines">@@ -235,6 +236,13 @@
</span><span class="cx"> m_isRunning = false;
</span><span class="cx"> for (NSString *keyName in sessionKVOProperties())
</span><span class="cx"> [m_session removeObserver:m_objcObserver.get() forKeyPath:keyName];
</span><ins>+
+ for (const auto& preview : m_previews) {
+ if (preview)
+ preview->invalidate();
+ }
+ m_previews.clear();
+
</ins><span class="cx"> shutdownCaptureSession();
</span><span class="cx"> m_session = nullptr;
</span><span class="cx"> }
</span><span class="lines">@@ -266,6 +274,45 @@
</span><span class="cx"> return nullptr;
</span><span class="cx"> }
</span><span class="cx">
</span><ins>+RefPtr<RealtimeMediaSourcePreview> AVMediaCaptureSource::preview()
+{
+ RefPtr<AVMediaSourcePreview> preview = createPreview();
+ if (!preview)
+ return nullptr;
+
+ m_previews.append(preview->createWeakPtr());
+ return preview.leakRef();
+}
+
+void AVMediaCaptureSource::removePreview(AVMediaSourcePreview* preview)
+{
+ size_t index;
+ for (index = 0; index < m_previews.size(); ++index) {
+ if (m_previews[index].get() == preview)
+ break;
+ }
+
+ if (index < m_previews.size())
+ m_previews.remove(index);
+}
+
+AVMediaSourcePreview::AVMediaSourcePreview(AVMediaCaptureSource* parent)
+ : m_parent(parent->createWeakPtr())
+{
+}
+
+AVMediaSourcePreview::~AVMediaSourcePreview()
+{
+ if (m_parent)
+ m_parent->removePreview(this);
+}
+
+void AVMediaSourcePreview::invalidate()
+{
+ m_parent = nullptr;
+ RealtimeMediaSourcePreview::invalidate();
+}
+
</ins><span class="cx"> NSArray* sessionKVOProperties()
</span><span class="cx"> {
</span><span class="cx"> static NSArray* keys = [@[@"running"] retain];
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVVideoCaptureSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -41,6 +41,7 @@
</span><span class="cx">
</span><span class="cx"> class FloatRect;
</span><span class="cx"> class GraphicsContext;
</span><ins>+class AVVideoSourcePreview;
</ins><span class="cx">
</span><span class="cx"> class AVVideoCaptureSource : public AVMediaCaptureSource {
</span><span class="cx"> public:
</span><span class="lines">@@ -77,8 +78,8 @@
</span><span class="cx"> void processNewFrame(RetainPtr<CMSampleBufferRef>);
</span><span class="cx">
</span><span class="cx"> void paintCurrentFrameInContext(GraphicsContext&, const FloatRect&) final;
</span><del>- PlatformLayer* platformLayer() const final;
</del><span class="cx">
</span><ins>+ RefPtr<AVMediaSourcePreview> createPreview() final;
</ins><span class="cx"> RetainPtr<CGImageRef> currentFrameCGImage();
</span><span class="cx"> RefPtr<Image> currentFrameImage() final;
</span><span class="cx">
</span><span class="lines">@@ -85,8 +86,8 @@
</span><span class="cx"> RetainPtr<NSString> m_pendingPreset;
</span><span class="cx"> RetainPtr<CMSampleBufferRef> m_buffer;
</span><span class="cx"> RetainPtr<CGImageRef> m_lastImage;
</span><ins>+
</ins><span class="cx"> Vector<Float64> m_videoFrameTimeStamps;
</span><del>- mutable RetainPtr<PlatformLayer> m_videoPreviewLayer;
</del><span class="cx"> Float64 m_frameRate { 0 };
</span><span class="cx"> int32_t m_width { 0 };
</span><span class="cx"> int32_t m_height { 0 };
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVVideoCaptureSourcemm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.mm (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.mm        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.mm        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -38,6 +38,7 @@
</span><span class="cx"> #import "NotImplemented.h"
</span><span class="cx"> #import "PlatformLayer.h"
</span><span class="cx"> #import "RealtimeMediaSourceCenter.h"
</span><ins>+#import "RealtimeMediaSourcePreview.h"
</ins><span class="cx"> #import "RealtimeMediaSourceSettings.h"
</span><span class="cx"> #import <AVFoundation/AVFoundation.h>
</span><span class="cx"> #import <objc/runtime.h>
</span><span class="lines">@@ -90,6 +91,90 @@
</span><span class="cx">
</span><span class="cx"> namespace WebCore {
</span><span class="cx">
</span><ins>+class AVVideoSourcePreview: public AVMediaSourcePreview {
+public:
+ static RefPtr<AVMediaSourcePreview> create(AVCaptureSession *, AVCaptureDeviceTypedef *, AVVideoCaptureSource*);
+
+private:
+ AVVideoSourcePreview(AVCaptureSession *, AVCaptureDeviceTypedef *, AVVideoCaptureSource*);
+
+ void invalidate() final;
+
+ void play() const final;
+ void pause() const final;
+ void setVolume(double) const final { };
+ void setEnabled(bool) final;
+ PlatformLayer* platformLayer() const final { return m_previewBackgroundLayer.get(); }
+
+ void setPaused(bool) const;
+
+ RetainPtr<AVCaptureVideoPreviewLayerType> m_previewLayer;
+ RetainPtr<PlatformLayer> m_previewBackgroundLayer;
+ RetainPtr<AVCaptureDeviceTypedef> m_device;
+};
+
+RefPtr<AVMediaSourcePreview> AVVideoSourcePreview::create(AVCaptureSession *session, AVCaptureDeviceTypedef* device, AVVideoCaptureSource* parent)
+{
+ return adoptRef(new AVVideoSourcePreview(session, device, parent));
+}
+
+AVVideoSourcePreview::AVVideoSourcePreview(AVCaptureSession *session, AVCaptureDeviceTypedef* device, AVVideoCaptureSource* parent)
+ : AVMediaSourcePreview(parent)
+{
+ m_device = device;
+ m_previewLayer = adoptNS([allocAVCaptureVideoPreviewLayerInstance() initWithSession:session]);
+#ifndef NDEBUG
+ m_previewLayer.get().name = @"AVVideoCaptureSource preview layer";
+#endif
+
+ m_previewLayer.get().contentsGravity = kCAGravityResize;
+ m_previewLayer.get().anchorPoint = CGPointZero;
+#if !PLATFORM(IOS)
+ m_previewLayer.get().autoresizingMask = kCALayerWidthSizable | kCALayerHeightSizable;
+#endif
+
+ m_previewBackgroundLayer = adoptNS([[CALayer alloc] init]);
+ m_previewBackgroundLayer.get().name = @"AVVideoSourcePreview parent layer";
+ m_previewBackgroundLayer.get().contentsGravity = kCAGravityResizeAspect;
+ m_previewBackgroundLayer.get().anchorPoint = CGPointZero;
+ m_previewBackgroundLayer.get().needsDisplayOnBoundsChange = YES;
+#if !PLATFORM(IOS)
+ m_previewBackgroundLayer.get().autoresizingMask = kCALayerWidthSizable | kCALayerHeightSizable;
+#endif
+
+ [m_previewBackgroundLayer addSublayer:m_previewLayer.get()];
+}
+
+void AVVideoSourcePreview::invalidate()
+{
+ m_previewLayer = nullptr;
+ m_previewBackgroundLayer = nullptr;
+ m_device = nullptr;
+ AVMediaSourcePreview::invalidate();
+}
+
+void AVVideoSourcePreview::play() const
+{
+ setPaused(false);
+}
+
+void AVVideoSourcePreview::pause() const
+{
+ setPaused(true);
+}
+
+void AVVideoSourcePreview::setPaused(bool paused) const
+{
+ [m_device lockForConfiguration:nil];
+ m_previewLayer.get().connection.enabled = !paused;
+ [m_device unlockForConfiguration];
+}
+
+void AVVideoSourcePreview::setEnabled(bool enabled)
+{
+ m_previewLayer.get().hidden = !enabled;
+}
+
</ins><span class="cx"> const OSType videoCaptureFormat = kCVPixelFormatType_32BGRA;
</span><span class="cx">
</span><span class="cx"> RefPtr<AVMediaCaptureSource> AVVideoCaptureSource::create(AVCaptureDeviceTypedef* device, const AtomicString& id, const MediaConstraints* constraints, String& invalidConstraint)
</span><span class="lines">@@ -215,7 +300,7 @@
</span><span class="cx"> {
</span><span class="cx"> NSString *preset = bestSessionPresetForVideoDimensions(size.width(), size.height());
</span><span class="cx"> if (!preset || ![session() canSetSessionPreset:preset]) {
</span><del>- LOG(Media, "AVVideoCaptureSource::applySize%p), unable find or set preset for width: %i, height: %i", this, size.width(), size.height());
</del><ins>+ LOG(Media, "AVVideoCaptureSource::applySize(%p), unable find or set preset for width: %i, height: %i", this, size.width(), size.height());
</ins><span class="cx"> return false;
</span><span class="cx"> }
</span><span class="cx">
</span><span class="lines">@@ -318,7 +403,6 @@
</span><span class="cx">
</span><span class="cx"> void AVVideoCaptureSource::shutdownCaptureSession()
</span><span class="cx"> {
</span><del>- m_videoPreviewLayer = nullptr;
</del><span class="cx"> m_buffer = nullptr;
</span><span class="cx"> m_lastImage = nullptr;
</span><span class="cx"> m_videoFrameTimeStamps.clear();
</span><span class="lines">@@ -365,12 +449,14 @@
</span><span class="cx"> ASSERT(newSampleBuffer);
</span><span class="cx">
</span><span class="cx"> CFArrayRef attachmentsArray = CMSampleBufferGetSampleAttachmentsArray(newSampleBuffer, true);
</span><del>- for (CFIndex i = 0; i < CFArrayGetCount(attachmentsArray); ++i) {
- CFMutableDictionaryRef attachments = (CFMutableDictionaryRef)CFArrayGetValueAtIndex(attachmentsArray, i);
- CFDictionarySetValue(attachments, kCMSampleAttachmentKey_DisplayImmediately, kCFBooleanTrue);
</del><ins>+ if (attachmentsArray) {
+ for (CFIndex i = 0; i < CFArrayGetCount(attachmentsArray); ++i) {
+ CFMutableDictionaryRef attachments = (CFMutableDictionaryRef)CFArrayGetValueAtIndex(attachmentsArray, i);
+ CFDictionarySetValue(attachments, kCMSampleAttachmentKey_DisplayImmediately, kCFBooleanTrue);
+ }
</ins><span class="cx"> }
</span><span class="cx">
</span><del>- m_buffer = newSampleBuffer;
</del><ins>+ m_buffer = adoptCF(newSampleBuffer);
</ins><span class="cx"> m_lastImage = nullptr;
</span><span class="cx">
</span><span class="cx"> bool settingsChanged = false;
</span><span class="lines">@@ -450,17 +536,9 @@
</span><span class="cx"> CGContextDrawImage(context.platformContext(), CGRectMake(0, 0, paintRect.width(), paintRect.height()), m_lastImage.get());
</span><span class="cx"> }
</span><span class="cx">
</span><del>-PlatformLayer* AVVideoCaptureSource::platformLayer() const
</del><ins>+RefPtr<AVMediaSourcePreview> AVVideoCaptureSource::createPreview()
</ins><span class="cx"> {
</span><del>- if (m_videoPreviewLayer)
- return m_videoPreviewLayer.get();
-
- m_videoPreviewLayer = adoptNS([allocAVCaptureVideoPreviewLayerInstance() initWithSession:session()]);
-#ifndef NDEBUG
- m_videoPreviewLayer.get().name = @"AVVideoCaptureSource preview layer";
-#endif
-
- return m_videoPreviewLayer.get();
</del><ins>+ return AVVideoSourcePreview::create(session(), device(), this);
</ins><span class="cx"> }
</span><span class="cx">
</span><span class="cx"> NSString *AVVideoCaptureSource::bestSessionPresetForVideoDimensions(Optional<int> width, Optional<int> height) const
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacMockRealtimeVideoSourceMach"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -54,8 +54,7 @@
</span><span class="cx"> RetainPtr<CMSampleBufferRef> CMSampleBufferFromPixelBuffer(CVPixelBufferRef);
</span><span class="cx"> RetainPtr<CVPixelBufferRef> pixelBufferFromCGImage(CGImageRef) const;
</span><span class="cx">
</span><del>- PlatformLayer* platformLayer() const override;
- void updatePlatformLayer() const override;
</del><ins>+ PlatformLayer* platformLayer() const;
</ins><span class="cx"> void updateSampleBuffer() override;
</span><span class="cx">
</span><span class="cx"> mutable RetainPtr<CGImageRef> m_previewImage;
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacMockRealtimeVideoSourceMacmm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.mm (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.mm        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mediastream/mac/MockRealtimeVideoSourceMac.mm        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -120,49 +120,6 @@
</span><span class="cx"> return adoptCF(pixelBuffer);
</span><span class="cx"> }
</span><span class="cx">
</span><del>-PlatformLayer* MockRealtimeVideoSourceMac::platformLayer() const
-{
- if (m_previewLayer)
- return m_previewLayer.get();
-
- m_previewLayer = adoptNS([[CALayer alloc] init]);
- m_previewLayer.get().name = @"MockRealtimeVideoSourceMac preview layer";
- m_previewLayer.get().contentsGravity = kCAGravityResizeAspect;
- m_previewLayer.get().anchorPoint = CGPointZero;
- m_previewLayer.get().needsDisplayOnBoundsChange = YES;
-#if !PLATFORM(IOS)
- m_previewLayer.get().autoresizingMask = kCALayerWidthSizable | kCALayerHeightSizable;
-#endif
-
- updatePlatformLayer();
-
- return m_previewLayer.get();
-}
-
-void MockRealtimeVideoSourceMac::updatePlatformLayer() const
-{
- if (!m_previewLayer)
- return;
-
- [CATransaction begin];
- [CATransaction setAnimationDuration:0];
- [CATransaction setDisableActions:YES];
-
- do {
- RefPtr<Image> image = imageBuffer()->copyImage();
- if (!image)
- break;
-
- m_previewImage = image->nativeImage();
- if (!m_previewImage)
- break;
-
- m_previewLayer.get().contents = (NSObject*)(m_previewImage.get());
- } while (0);
-
- [CATransaction commit];
-}
-
</del><span class="cx"> void MockRealtimeVideoSourceMac::updateSampleBuffer()
</span><span class="cx"> {
</span><span class="cx"> auto pixelBuffer = pixelBufferFromCGImage(imageBuffer()->copyImage()->nativeImage().get());
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeVideoSourcecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.cpp (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.cpp        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.cpp        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -138,7 +138,6 @@
</span><span class="cx"> if (m_timer.isActive())
</span><span class="cx"> m_timer.startRepeating(std::chrono::milliseconds(lround(1000 / rate)));
</span><span class="cx">
</span><del>- updatePlatformLayer();
</del><span class="cx"> updateSampleBuffer();
</span><span class="cx"> return true;
</span><span class="cx"> }
</span><span class="lines">@@ -168,7 +167,6 @@
</span><span class="cx"> m_statsFont.update(nullptr);
</span><span class="cx">
</span><span class="cx"> m_imageBuffer = nullptr;
</span><del>- updatePlatformLayer();
</del><span class="cx">
</span><span class="cx"> return true;
</span><span class="cx"> }
</span><span class="lines">@@ -339,7 +337,6 @@
</span><span class="cx"> drawAnimation(context);
</span><span class="cx"> drawBoxes(context);
</span><span class="cx">
</span><del>- updatePlatformLayer();
</del><span class="cx"> updateSampleBuffer();
</span><span class="cx"> }
</span><span class="cx">
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeVideoSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.h (208850 => 208851)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.h        2016-11-17 18:19:55 UTC (rev 208850)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.h        2016-11-17 18:43:40 UTC (rev 208851)
</span><span class="lines">@@ -53,7 +53,6 @@
</span><span class="cx">
</span><span class="cx"> protected:
</span><span class="cx"> MockRealtimeVideoSource(const String&);
</span><del>- virtual void updatePlatformLayer() const { }
</del><span class="cx"> virtual void updateSampleBuffer() { }
</span><span class="cx">
</span><span class="cx"> ImageBuffer* imageBuffer() const;
</span><span class="lines">@@ -77,7 +76,6 @@
</span><span class="cx"> bool applyFacingMode(RealtimeMediaSourceSettings::VideoFacingMode) override { return true; }
</span><span class="cx"> bool applyAspectRatio(double) override { return true; }
</span><span class="cx">
</span><del>- PlatformLayer* platformLayer() const override { return nullptr; }
</del><span class="cx"> RefPtr<Image> currentFrameImage() override;
</span><span class="cx"> void paintCurrentFrameInContext(GraphicsContext&, const FloatRect&) override;
</span><span class="cx">
</span></span></pre>
</div>
</div>
</body>
</html>