<!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>[213941] trunk/Source</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/213941">213941</a></dd>
<dt>Author</dt> <dd>jer.noble@apple.com</dd>
<dt>Date</dt> <dd>2017-03-14 14:41:48 -0700 (Tue, 14 Mar 2017)</dd>
</dl>

<h3>Log Message</h3>
<pre>Refactor: Allow WebKit2 to override the creation of RealtimeMediaSources
https://bugs.webkit.org/show_bug.cgi?id=169227

Reviewed by Eric Carlson.

Source/WebCore:

Allow clients of RealtimeMediaSourceCenter to specify a factory for creating
RealtimeMediaSources, to be used by subclasess of RealtimeMediaSourceCenter. Add virtual
methods to retrieve the &quot;default&quot; factories for the RealtimeMediaSourceCenter subclass. The
requires moving the creation of sources up from CaptureDeviceManager into
RealtimeMediaSourceCenterMac, and the addition of factory methods to AVAudioCaptureSource
and AVVideoCaptureSource.

* platform/mediastream/CaptureDeviceManager.cpp:
(CaptureDeviceManager::deviceWithUID):
(CaptureDeviceManager::bestSourcesForTypeAndConstraints): Deleted.
(CaptureDeviceManager::sourceWithUID): Deleted.
* platform/mediastream/CaptureDeviceManager.h:
* platform/mediastream/RealtimeMediaSource.h:
* platform/mediastream/RealtimeMediaSourceCenter.cpp:
(WebCore::RealtimeMediaSourceCenter::setAudioFactory):
(WebCore::RealtimeMediaSourceCenter::unsetAudioFactory):
(WebCore::RealtimeMediaSourceCenter::setVideoFactory):
(WebCore::RealtimeMediaSourceCenter::unsetVideoFactory):
* platform/mediastream/RealtimeMediaSourceCenter.h:
(WebCore::RealtimeMediaSourceCenter::audioFactory):
(WebCore::RealtimeMediaSourceCenter::videoFactory):
* platform/mediastream/mac/AVAudioCaptureSource.h:
* platform/mediastream/mac/AVAudioCaptureSource.mm:
(WebCore::AVAudioCaptureSource::factory):
* platform/mediastream/mac/AVCaptureDeviceManager.h:
* platform/mediastream/mac/AVCaptureDeviceManager.mm:
(WebCore::AVCaptureDeviceManager::createMediaSourceForCaptureDeviceWithConstraints): Deleted.
* platform/mediastream/mac/AVMediaCaptureSource.h:
* platform/mediastream/mac/AVVideoCaptureSource.h:
* platform/mediastream/mac/AVVideoCaptureSource.mm:
(WebCore::AVVideoCaptureSource::factory):
* platform/mediastream/mac/RealtimeMediaSourceCenterMac.cpp:
(WebCore::RealtimeMediaSourceCenterMac::RealtimeMediaSourceCenterMac):
(WebCore::RealtimeMediaSourceCenterMac::validateRequestConstraints):
(WebCore::RealtimeMediaSourceCenterMac::createMediaStream):
(WebCore::RealtimeMediaSourceCenterMac::bestSourcesForTypeAndConstraints):
(WebCore::RealtimeMediaSourceCenterMac::defaultAudioFactory):
(WebCore::RealtimeMediaSourceCenterMac::defaultVideoFactory):
* platform/mediastream/mac/RealtimeMediaSourceCenterMac.h:
* platform/mock/MockRealtimeAudioSource.cpp:
(WebCore::MockRealtimeAudioSource::factory):
* platform/mock/MockRealtimeAudioSource.h:
* platform/mock/MockRealtimeMediaSourceCenter.cpp:
(WebCore::MockRealtimeMediaSourceCenter::defaultAudioFactory):
(WebCore::MockRealtimeMediaSourceCenter::defaultVideoFactory):
* platform/mock/MockRealtimeMediaSourceCenter.h:
* platform/mock/MockRealtimeVideoSource.cpp:
(WebCore::MockRealtimeVideoSource::factory):
* platform/mock/MockRealtimeVideoSource.h:

Source/WebKit2:

* WebKit2.xcodeproj/project.pbxproj:
* WebProcess/WebCoreSupport/WebUserMediaClient.cpp:
(WebKit::WebUserMediaClient::WebUserMediaClient):
(WebKit::WebUserMediaClient::initializeFactories): Add empty non-Cocoa implementation.
* WebProcess/WebCoreSupport/WebUserMediaClient.h:
* WebProcess/WebCoreSupport/cocoa/WebUserMediaClientMac.mm: Added.
(WebKit::WebUserMediaClient::initializeFactories): Initialize a (for now) pass-through factory.</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamCaptureDeviceManagercpp">trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamCaptureDeviceManagerh">trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceh">trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceCentercpp">trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceCenterh">trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.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="#trunkSourceWebCoreplatformmediastreammacAVCaptureDeviceManagerh">trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVCaptureDeviceManagermm">trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.mm</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacAVMediaCaptureSourceh">trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h</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="#trunkSourceWebCoreplatformmediastreammacRealtimeMediaSourceCenterMaccpp">trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmediastreammacRealtimeMediaSourceCenterMach">trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmockMockRealtimeAudioSourcecpp">trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmockMockRealtimeAudioSourceh">trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmockMockRealtimeMediaSourceCentercpp">trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformmockMockRealtimeMediaSourceCenterh">trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.h</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>
<li><a href="#trunkSourceWebKit2ChangeLog">trunk/Source/WebKit2/ChangeLog</a></li>
<li><a href="#trunkSourceWebKit2WebKit2xcodeprojprojectpbxproj">trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceWebKit2WebProcessWebCoreSupportWebUserMediaClientcpp">trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.cpp</a></li>
<li><a href="#trunkSourceWebKit2WebProcessWebCoreSupportWebUserMediaClienth">trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.h</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li>trunk/Source/WebKit2/WebProcess/WebCoreSupport/cocoa/</li>
<li><a href="#trunkSourceWebKit2WebProcessWebCoreSupportcocoaWebUserMediaClientMacmm">trunk/Source/WebKit2/WebProcess/WebCoreSupport/cocoa/WebUserMediaClientMac.mm</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/ChangeLog        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -1,3 +1,60 @@
</span><ins>+2017-03-06  Jer Noble  &lt;jer.noble@apple.com&gt;
+
+        Refactor: Allow WebKit2 to override the creation of RealtimeMediaSources
+        https://bugs.webkit.org/show_bug.cgi?id=169227
+
+        Reviewed by Eric Carlson.
+
+        Allow clients of RealtimeMediaSourceCenter to specify a factory for creating
+        RealtimeMediaSources, to be used by subclasess of RealtimeMediaSourceCenter. Add virtual
+        methods to retrieve the &quot;default&quot; factories for the RealtimeMediaSourceCenter subclass. The
+        requires moving the creation of sources up from CaptureDeviceManager into
+        RealtimeMediaSourceCenterMac, and the addition of factory methods to AVAudioCaptureSource
+        and AVVideoCaptureSource.
+
+        * platform/mediastream/CaptureDeviceManager.cpp:
+        (CaptureDeviceManager::deviceWithUID):
+        (CaptureDeviceManager::bestSourcesForTypeAndConstraints): Deleted.
+        (CaptureDeviceManager::sourceWithUID): Deleted.
+        * platform/mediastream/CaptureDeviceManager.h:
+        * platform/mediastream/RealtimeMediaSource.h:
+        * platform/mediastream/RealtimeMediaSourceCenter.cpp:
+        (WebCore::RealtimeMediaSourceCenter::setAudioFactory):
+        (WebCore::RealtimeMediaSourceCenter::unsetAudioFactory):
+        (WebCore::RealtimeMediaSourceCenter::setVideoFactory):
+        (WebCore::RealtimeMediaSourceCenter::unsetVideoFactory):
+        * platform/mediastream/RealtimeMediaSourceCenter.h:
+        (WebCore::RealtimeMediaSourceCenter::audioFactory):
+        (WebCore::RealtimeMediaSourceCenter::videoFactory):
+        * platform/mediastream/mac/AVAudioCaptureSource.h:
+        * platform/mediastream/mac/AVAudioCaptureSource.mm:
+        (WebCore::AVAudioCaptureSource::factory):
+        * platform/mediastream/mac/AVCaptureDeviceManager.h:
+        * platform/mediastream/mac/AVCaptureDeviceManager.mm:
+        (WebCore::AVCaptureDeviceManager::createMediaSourceForCaptureDeviceWithConstraints): Deleted.
+        * platform/mediastream/mac/AVMediaCaptureSource.h:
+        * platform/mediastream/mac/AVVideoCaptureSource.h:
+        * platform/mediastream/mac/AVVideoCaptureSource.mm:
+        (WebCore::AVVideoCaptureSource::factory):
+        * platform/mediastream/mac/RealtimeMediaSourceCenterMac.cpp:
+        (WebCore::RealtimeMediaSourceCenterMac::RealtimeMediaSourceCenterMac):
+        (WebCore::RealtimeMediaSourceCenterMac::validateRequestConstraints):
+        (WebCore::RealtimeMediaSourceCenterMac::createMediaStream):
+        (WebCore::RealtimeMediaSourceCenterMac::bestSourcesForTypeAndConstraints):
+        (WebCore::RealtimeMediaSourceCenterMac::defaultAudioFactory):
+        (WebCore::RealtimeMediaSourceCenterMac::defaultVideoFactory):
+        * platform/mediastream/mac/RealtimeMediaSourceCenterMac.h:
+        * platform/mock/MockRealtimeAudioSource.cpp:
+        (WebCore::MockRealtimeAudioSource::factory):
+        * platform/mock/MockRealtimeAudioSource.h:
+        * platform/mock/MockRealtimeMediaSourceCenter.cpp:
+        (WebCore::MockRealtimeMediaSourceCenter::defaultAudioFactory):
+        (WebCore::MockRealtimeMediaSourceCenter::defaultVideoFactory):
+        * platform/mock/MockRealtimeMediaSourceCenter.h:
+        * platform/mock/MockRealtimeVideoSource.cpp:
+        (WebCore::MockRealtimeVideoSource::factory):
+        * platform/mock/MockRealtimeVideoSource.h:
+
</ins><span class="cx"> 2017-03-14  Dean Jackson  &lt;dino@apple.com&gt;
</span><span class="cx"> 
</span><span class="cx">         Rename LayerTypeWebGLLayer and use it for both WebGL and WebGPU
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamCaptureDeviceManagercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.cpp (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.cpp        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.cpp        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -69,42 +69,9 @@
</span><span class="cx">     return false;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Vector&lt;String&gt; CaptureDeviceManager::bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type type, const MediaConstraints&amp; constraints, String&amp; invalidConstraint)
</del><ins>+std::optional&lt;CaptureDevice&gt; CaptureDeviceManager::deviceWithUID(const String&amp; deviceUID, RealtimeMediaSource::Type type)
</ins><span class="cx"> {
</span><del>-    Vector&lt;RefPtr&lt;RealtimeMediaSource&gt;&gt; bestSources;
-
-    struct {
-        bool operator()(RefPtr&lt;RealtimeMediaSource&gt; a, RefPtr&lt;RealtimeMediaSource&gt; b)
-        {
-            return a-&gt;fitnessScore() &lt; b-&gt;fitnessScore();
-        }
-    } sortBasedOnFitnessScore;
-
-    ASSERT(type != RealtimeMediaSource::Type::None);
-    CaptureDevice::DeviceType deviceType = type == RealtimeMediaSource::Type::Video ? CaptureDevice::DeviceType::Video : CaptureDevice::DeviceType::Audio;
</del><span class="cx">     for (auto&amp; captureDevice : captureDevices()) {
</span><del>-        if (!captureDevice.enabled() || captureDevice.type() != deviceType)
-            continue;
-
-        if (auto captureSource = createMediaSourceForCaptureDeviceWithConstraints(captureDevice, &amp;constraints, invalidConstraint))
-            bestSources.append(captureSource.leakRef());
-    }
-
-    Vector&lt;String&gt; sourceUIDs;
-    if (bestSources.isEmpty())
-        return sourceUIDs;
-
-    sourceUIDs.reserveInitialCapacity(bestSources.size());
-    std::sort(bestSources.begin(), bestSources.end(), sortBasedOnFitnessScore);
-    for (auto&amp; device : bestSources)
-        sourceUIDs.uncheckedAppend(device-&gt;persistentID());
-
-    return sourceUIDs;
-}
-
-RefPtr&lt;RealtimeMediaSource&gt; CaptureDeviceManager::sourceWithUID(const String&amp; deviceUID, RealtimeMediaSource::Type type, const MediaConstraints* constraints, String&amp; invalidConstraint)
-{
-    for (auto&amp; captureDevice : captureDevices()) {
</del><span class="cx">         CaptureDevice::DeviceType deviceType;
</span><span class="cx"> 
</span><span class="cx">         switch (type) {
</span><span class="lines">@@ -124,11 +91,10 @@
</span><span class="cx">         if (!captureDevice.enabled())
</span><span class="cx">             continue;
</span><span class="cx"> 
</span><del>-        if (auto mediaSource = createMediaSourceForCaptureDeviceWithConstraints(captureDevice, constraints, invalidConstraint))
-            return mediaSource;
</del><ins>+        return captureDevice;
</ins><span class="cx">     }
</span><span class="cx"> 
</span><del>-    return nullptr;
</del><ins>+    return std::nullopt;
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(MEDIA_STREAM)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamCaptureDeviceManagerh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/CaptureDeviceManager.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -37,13 +37,10 @@
</span><span class="cx">     virtual Vector&lt;CaptureDevice&gt;&amp; captureDevices() = 0;
</span><span class="cx">     virtual void refreshCaptureDevices() { }
</span><span class="cx">     virtual Vector&lt;CaptureDevice&gt; getSourcesInfo();
</span><del>-    virtual Vector&lt;String&gt; bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type, const MediaConstraints&amp;, String&amp;);
-    virtual RefPtr&lt;RealtimeMediaSource&gt; sourceWithUID(const String&amp;, RealtimeMediaSource::Type, const MediaConstraints*, String&amp;);
</del><ins>+    virtual std::optional&lt;CaptureDevice&gt; deviceWithUID(const String&amp;, RealtimeMediaSource::Type);
</ins><span class="cx"> 
</span><span class="cx"> protected:
</span><span class="cx">     virtual ~CaptureDeviceManager();
</span><del>-    virtual RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp;, const MediaConstraints*, String&amp;) = 0;
-
</del><span class="cx">     bool captureDeviceFromDeviceID(const String&amp; captureDeviceID, CaptureDevice&amp; source);
</span><span class="cx"> };
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/RealtimeMediaSource.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -54,6 +54,7 @@
</span><span class="cx"> namespace WebCore {
</span><span class="cx"> 
</span><span class="cx"> class AudioStreamDescription;
</span><ins>+class CaptureDevice;
</ins><span class="cx"> class FloatRect;
</span><span class="cx"> class GraphicsContext;
</span><span class="cx"> class MediaStreamPrivate;
</span><span class="lines">@@ -82,6 +83,15 @@
</span><span class="cx">         virtual void audioSamplesAvailable(const MediaTime&amp;, const PlatformAudioData&amp;, const AudioStreamDescription&amp;, size_t /*numberOfFrames*/) { }
</span><span class="cx">     };
</span><span class="cx"> 
</span><ins>+    class CaptureFactory {
+    public:
+        virtual ~CaptureFactory() = default;
+        virtual RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp;, const MediaConstraints*, String&amp;) = 0;
+
+    protected:
+        CaptureFactory() = default;
+    };
+
</ins><span class="cx">     virtual ~RealtimeMediaSource() { }
</span><span class="cx"> 
</span><span class="cx">     const String&amp; id() const { return m_id; }
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceCentercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.cpp (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.cpp        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.cpp        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -66,6 +66,28 @@
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+void RealtimeMediaSourceCenter::setAudioFactory(RealtimeMediaSource::CaptureFactory&amp; factory)
+{
+    m_audioFactory = &amp;factory;
+}
+
+void RealtimeMediaSourceCenter::unsetAudioFactory(RealtimeMediaSource::CaptureFactory&amp; factory)
+{
+    if (m_audioFactory == &amp;factory)
+        m_audioFactory = nullptr;
+}
+
+void RealtimeMediaSourceCenter::setVideoFactory(RealtimeMediaSource::CaptureFactory&amp; factory)
+{
+    m_videoFactory = &amp;factory;
+}
+
+void RealtimeMediaSourceCenter::unsetVideoFactory(RealtimeMediaSource::CaptureFactory&amp; factory)
+{
+    if (m_videoFactory == &amp;factory)
+        m_videoFactory = nullptr;
+}
+
</ins><span class="cx"> } // namespace WebCore
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(MEDIA_STREAM)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreamRealtimeMediaSourceCenterh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/RealtimeMediaSourceCenter.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -65,11 +65,25 @@
</span><span class="cx">     
</span><span class="cx">     virtual const RealtimeMediaSourceSupportedConstraints&amp; supportedConstraints() { return m_supportedConstraints; }
</span><span class="cx"> 
</span><ins>+    virtual RealtimeMediaSource::CaptureFactory* defaultAudioFactory() { return nullptr; }
+    virtual RealtimeMediaSource::CaptureFactory* defaultVideoFactory() { return nullptr; }
+
+    WEBCORE_EXPORT void setAudioFactory(RealtimeMediaSource::CaptureFactory&amp;);
+    WEBCORE_EXPORT void unsetAudioFactory(RealtimeMediaSource::CaptureFactory&amp;);
+    RealtimeMediaSource::CaptureFactory* audioFactory() const { return m_audioFactory; }
+
+    WEBCORE_EXPORT void setVideoFactory(RealtimeMediaSource::CaptureFactory&amp;);
+    WEBCORE_EXPORT void unsetVideoFactory(RealtimeMediaSource::CaptureFactory&amp;);
+    RealtimeMediaSource::CaptureFactory* videoFactory() const { return m_videoFactory; }
+
</ins><span class="cx"> protected:
</span><span class="cx">     RealtimeMediaSourceCenter();
</span><span class="cx"> 
</span><span class="cx">     static RealtimeMediaSourceCenter&amp; platformCenter();
</span><span class="cx">     RealtimeMediaSourceSupportedConstraints m_supportedConstraints;
</span><ins>+
+    RealtimeMediaSource::CaptureFactory* m_audioFactory { nullptr };
+    RealtimeMediaSource::CaptureFactory* m_videoFactory { nullptr };
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> } // namespace WebCore
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVAudioCaptureSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -46,6 +46,8 @@
</span><span class="cx"> 
</span><span class="cx">     static RefPtr&lt;AVMediaCaptureSource&gt; create(AVCaptureDevice*, const AtomicString&amp;, const MediaConstraints*, String&amp;);
</span><span class="cx"> 
</span><ins>+    WEBCORE_EXPORT static CaptureFactory&amp; factory();
+
</ins><span class="cx"> private:
</span><span class="cx">     AVAudioCaptureSource(AVCaptureDevice*, const AtomicString&amp;);
</span><span class="cx">     virtual ~AVAudioCaptureSource();
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVAudioCaptureSourcemm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.mm (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.mm        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVAudioCaptureSource.mm        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -30,6 +30,7 @@
</span><span class="cx"> 
</span><span class="cx"> #import &quot;AudioSampleBufferList.h&quot;
</span><span class="cx"> #import &quot;CAAudioStreamDescription.h&quot;
</span><ins>+#import &quot;CaptureDevice.h&quot;
</ins><span class="cx"> #import &quot;Logging.h&quot;
</span><span class="cx"> #import &quot;MediaConstraints.h&quot;
</span><span class="cx"> #import &quot;MediaSampleAVFObjC.h&quot;
</span><span class="lines">@@ -41,6 +42,7 @@
</span><span class="cx"> #import &lt;AVFoundation/AVCaptureSession.h&gt;
</span><span class="cx"> #import &lt;CoreAudio/CoreAudioTypes.h&gt;
</span><span class="cx"> #import &lt;wtf/HashSet.h&gt;
</span><ins>+#import &lt;wtf/NeverDestroyed.h&gt;
</ins><span class="cx"> 
</span><span class="cx"> #import &quot;CoreMediaSoftLink.h&quot;
</span><span class="cx"> 
</span><span class="lines">@@ -75,6 +77,15 @@
</span><span class="cx"> 
</span><span class="cx"> namespace WebCore {
</span><span class="cx"> 
</span><ins>+class AVAudioCaptureSourceFactory : public RealtimeMediaSource::CaptureFactory {
+public:
+    RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp; captureDevice, const MediaConstraints* constraints, String&amp; invalidConstraint) final {
+        AVCaptureDeviceTypedef *device = [getAVCaptureDeviceClass() deviceWithUniqueID:captureDevice.persistentId()];
+        ASSERT(!device || (device &amp;&amp; captureDevice.type() == CaptureDevice::DeviceType::Audio));
+        return device ? AVAudioCaptureSource::create(device, emptyString(), constraints, invalidConstraint) : nullptr;
+    }
+};
+
</ins><span class="cx"> RefPtr&lt;AVMediaCaptureSource&gt; AVAudioCaptureSource::create(AVCaptureDeviceTypedef* device, const AtomicString&amp; id, const MediaConstraints* constraints, String&amp; invalidConstraint)
</span><span class="cx"> {
</span><span class="cx">     auto source = adoptRef(new AVAudioCaptureSource(device, id));
</span><span class="lines">@@ -89,6 +100,12 @@
</span><span class="cx">     return source;
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+RealtimeMediaSource::CaptureFactory&amp; AVAudioCaptureSource::factory()
+{
+    static NeverDestroyed&lt;AVAudioCaptureSourceFactory&gt; factory;
+    return factory.get();
+}
+
</ins><span class="cx"> AVAudioCaptureSource::AVAudioCaptureSource(AVCaptureDeviceTypedef* device, const AtomicString&amp; id)
</span><span class="cx">     : AVMediaCaptureSource(device, id, Type::Audio)
</span><span class="cx"> {
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVCaptureDeviceManagerh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -60,7 +60,6 @@
</span><span class="cx">     AVCaptureDeviceManager();
</span><span class="cx">     ~AVCaptureDeviceManager() final;
</span><span class="cx"> 
</span><del>-    RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp;, const MediaConstraints*, String&amp;) final;
</del><span class="cx">     void refreshCaptureDevices() final;
</span><span class="cx">     void registerForDeviceNotifications();
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVCaptureDeviceManagermm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.mm (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.mm        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVCaptureDeviceManager.mm        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -176,18 +176,6 @@
</span><span class="cx">     return CaptureDeviceManager::getSourcesInfo();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-RefPtr&lt;RealtimeMediaSource&gt; AVCaptureDeviceManager::createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp; captureDevice, const MediaConstraints* constraints, String&amp; invalidConstraint)
-{
-    AVCaptureDeviceTypedef *device = [getAVCaptureDeviceClass() deviceWithUniqueID:captureDevice.persistentId()];
-    if (!device)
-        return nullptr;
-
-    if (captureDevice.type() == CaptureDevice::DeviceType::Audio)
-        return AVAudioCaptureSource::create(device, emptyString(), constraints, invalidConstraint);
-
-    return AVVideoCaptureSource::create(device, emptyString(), constraints, invalidConstraint);
-}
-
</del><span class="cx"> void AVCaptureDeviceManager::registerForDeviceNotifications()
</span><span class="cx"> {
</span><span class="cx">     [[NSNotificationCenter defaultCenter] addObserver:m_objcObserver.get() selector:@selector(deviceConnected:) name:AVCaptureDeviceWasConnectedNotification object:nil];
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVMediaCaptureSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVMediaCaptureSource.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -40,6 +40,7 @@
</span><span class="cx"> OBJC_CLASS AVCaptureSession;
</span><span class="cx"> OBJC_CLASS AVCaptureVideoDataOutput;
</span><span class="cx"> OBJC_CLASS NSError;
</span><ins>+OBJC_CLASS NSNotification;
</ins><span class="cx"> OBJC_CLASS WebCoreAVMediaCaptureSourceObserver;
</span><span class="cx"> 
</span><span class="cx"> typedef struct opaqueCMSampleBuffer *CMSampleBufferRef;
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVVideoCaptureSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -47,6 +47,8 @@
</span><span class="cx"> public:
</span><span class="cx">     static RefPtr&lt;AVMediaCaptureSource&gt; create(AVCaptureDevice*, const AtomicString&amp;, const MediaConstraints*, String&amp;);
</span><span class="cx"> 
</span><ins>+    WEBCORE_EXPORT static CaptureFactory&amp; factory();
+
</ins><span class="cx">     int32_t width() const { return m_width; }
</span><span class="cx">     int32_t height() const { return m_height; }
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacAVVideoCaptureSourcemm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.mm (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.mm        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/AVVideoCaptureSource.mm        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -109,6 +109,15 @@
</span><span class="cx"> const OSType videoCaptureFormat = kCVPixelFormatType_420YpCbCr8BiPlanarFullRange;
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><ins>+class AVVideoCaptureSourceFactory : public RealtimeMediaSource::CaptureFactory {
+public:
+    RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp; captureDevice, const MediaConstraints* constraints, String&amp; invalidConstraint) final {
+        AVCaptureDeviceTypedef *device = [getAVCaptureDeviceClass() deviceWithUniqueID:captureDevice.persistentId()];
+        ASSERT(!device || (captureDevice.type() == CaptureDevice::DeviceType::Video));
+        return device ? AVVideoCaptureSource::create(device, emptyString(), constraints, invalidConstraint) : nullptr;
+    }
+};
+
</ins><span class="cx"> RefPtr&lt;AVMediaCaptureSource&gt; AVVideoCaptureSource::create(AVCaptureDeviceTypedef* device, const AtomicString&amp; id, const MediaConstraints* constraints, String&amp; invalidConstraint)
</span><span class="cx"> {
</span><span class="cx">     auto source = adoptRef(new AVVideoCaptureSource(device, id));
</span><span class="lines">@@ -123,6 +132,12 @@
</span><span class="cx">     return source;
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+RealtimeMediaSource::CaptureFactory&amp; AVVideoCaptureSource::factory()
+{
+    static NeverDestroyed&lt;AVVideoCaptureSourceFactory&gt; factory;
+    return factory.get();
+}
+
</ins><span class="cx"> AVVideoCaptureSource::AVVideoCaptureSource(AVCaptureDeviceTypedef* device, const AtomicString&amp; id)
</span><span class="cx">     : AVMediaCaptureSource(device, id, Type::Video)
</span><span class="cx"> {
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacRealtimeMediaSourceCenterMaccpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.cpp (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.cpp        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.cpp        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -33,7 +33,9 @@
</span><span class="cx"> #if ENABLE(MEDIA_STREAM)
</span><span class="cx"> #include &quot;RealtimeMediaSourceCenterMac.h&quot;
</span><span class="cx"> 
</span><ins>+#include &quot;AVAudioCaptureSource.h&quot;
</ins><span class="cx"> #include &quot;AVCaptureDeviceManager.h&quot;
</span><ins>+#include &quot;AVVideoCaptureSource.h&quot;
</ins><span class="cx"> #include &quot;Logging.h&quot;
</span><span class="cx"> #include &quot;MediaStreamPrivate.h&quot;
</span><span class="cx"> #include &lt;wtf/MainThread.h&gt;
</span><span class="lines">@@ -60,6 +62,9 @@
</span><span class="cx">     m_supportedConstraints.setSupportsEchoCancellation(false);
</span><span class="cx">     m_supportedConstraints.setSupportsDeviceId(true);
</span><span class="cx">     m_supportedConstraints.setSupportsGroupId(true);
</span><ins>+
+    m_audioFactory = &amp;AVAudioCaptureSource::factory();
+    m_videoFactory = &amp;AVVideoCaptureSource::factory();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> RealtimeMediaSourceCenterMac::~RealtimeMediaSourceCenterMac()
</span><span class="lines">@@ -73,7 +78,7 @@
</span><span class="cx">     String invalidConstraint;
</span><span class="cx"> 
</span><span class="cx">     if (audioConstraints.isValid()) {
</span><del>-        audioSourceUIDs = AVCaptureDeviceManager::singleton().bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type::Audio, audioConstraints, invalidConstraint);
</del><ins>+        audioSourceUIDs = bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type::Audio, audioConstraints, invalidConstraint);
</ins><span class="cx">         if (!invalidConstraint.isEmpty()) {
</span><span class="cx">             invalidHandler(invalidConstraint);
</span><span class="cx">             return;
</span><span class="lines">@@ -81,7 +86,7 @@
</span><span class="cx">     }
</span><span class="cx"> 
</span><span class="cx">     if (videoConstraints.isValid()) {
</span><del>-        videoSourceUIDs = AVCaptureDeviceManager::singleton().bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type::Video, videoConstraints, invalidConstraint);
</del><ins>+        videoSourceUIDs = bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type::Video, videoConstraints, invalidConstraint);
</ins><span class="cx">         if (!invalidConstraint.isEmpty()) {
</span><span class="cx">             invalidHandler(invalidConstraint);
</span><span class="cx">             return;
</span><span class="lines">@@ -98,23 +103,26 @@
</span><span class="cx">     String invalidConstraint;
</span><span class="cx"> 
</span><span class="cx">     if (!audioDeviceID.isEmpty()) {
</span><del>-        auto audioSource = AVCaptureDeviceManager::singleton().sourceWithUID(audioDeviceID, RealtimeMediaSource::Type::Audio, audioConstraints, invalidConstraint);
</del><ins>+        auto audioDevice = AVCaptureDeviceManager::singleton().deviceWithUID(audioDeviceID, RealtimeMediaSource::Type::Audio);
+        if (audioDevice &amp;&amp; m_audioFactory) {
+            if (auto audioSource = m_audioFactory-&gt;createMediaSourceForCaptureDeviceWithConstraints(audioDevice.value(), audioConstraints, invalidConstraint))
+                audioSources.append(audioSource.releaseNonNull());
</ins><span class="cx"> #if !LOG_DISABLED
</span><del>-        if (!invalidConstraint.isEmpty())
-            LOG(Media, &quot;RealtimeMediaSourceCenterMac::createMediaStream(%p), audio constraints failed to apply: %s&quot;, this, invalidConstraint.utf8().data());
</del><ins>+            if (!invalidConstraint.isEmpty())
+                LOG(Media, &quot;RealtimeMediaSourceCenterMac::createMediaStream(%p), audio constraints failed to apply: %s&quot;, this, invalidConstraint.utf8().data());
</ins><span class="cx"> #endif
</span><del>-
-        if (audioSource)
-            audioSources.append(audioSource.releaseNonNull());
</del><ins>+        }
</ins><span class="cx">     }
</span><span class="cx">     if (!videoDeviceID.isEmpty()) {
</span><del>-        auto videoSource = AVCaptureDeviceManager::singleton().sourceWithUID(videoDeviceID, RealtimeMediaSource::Type::Video, videoConstraints, invalidConstraint);
</del><ins>+        auto videoDevice = AVCaptureDeviceManager::singleton().deviceWithUID(videoDeviceID, RealtimeMediaSource::Type::Video);
+        if (videoDevice &amp;&amp; m_videoFactory) {
+            if (auto videoSource = m_videoFactory-&gt;createMediaSourceForCaptureDeviceWithConstraints(videoDevice.value(), videoConstraints, invalidConstraint))
+                videoSources.append(videoSource.releaseNonNull());
</ins><span class="cx"> #if !LOG_DISABLED
</span><span class="cx">         if (!invalidConstraint.isEmpty())
</span><span class="cx">             LOG(Media, &quot;RealtimeMediaSourceCenterMac::createMediaStream(%p), video constraints failed to apply: %s&quot;, this, invalidConstraint.utf8().data());
</span><span class="cx"> #endif
</span><del>-        if (videoSource)
-            videoSources.append(videoSource.releaseNonNull());
</del><ins>+        }
</ins><span class="cx">     }
</span><span class="cx"> 
</span><span class="cx">     if (videoSources.isEmpty() &amp;&amp; audioSources.isEmpty())
</span><span class="lines">@@ -128,6 +136,52 @@
</span><span class="cx">     return AVCaptureDeviceManager::singleton().getSourcesInfo();
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+Vector&lt;String&gt; RealtimeMediaSourceCenterMac::bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type type, const MediaConstraints&amp; constraints, String&amp; invalidConstraint)
+{
+    Vector&lt;RefPtr&lt;RealtimeMediaSource&gt;&gt; bestSources;
+
+    struct {
+        bool operator()(RefPtr&lt;RealtimeMediaSource&gt; a, RefPtr&lt;RealtimeMediaSource&gt; b)
+        {
+            return a-&gt;fitnessScore() &lt; b-&gt;fitnessScore();
+        }
+    } sortBasedOnFitnessScore;
+
+    CaptureDevice::DeviceType deviceType = type == RealtimeMediaSource::Type::Video ? CaptureDevice::DeviceType::Video : CaptureDevice::DeviceType::Audio;
+    for (auto&amp; captureDevice : getMediaStreamDevices()) {
+        if (!captureDevice.enabled() || captureDevice.type() != deviceType)
+            continue;
+
+        RealtimeMediaSource::CaptureFactory* factory = type == RealtimeMediaSource::Type::Video ? m_videoFactory : m_audioFactory;
+        if (!factory)
+            continue;
+
+        if (auto captureSource = factory-&gt;createMediaSourceForCaptureDeviceWithConstraints(captureDevice, &amp;constraints, invalidConstraint))
+            bestSources.append(captureSource.leakRef());
+    }
+
+    Vector&lt;String&gt; sourceUIDs;
+    if (bestSources.isEmpty())
+        return sourceUIDs;
+
+    sourceUIDs.reserveInitialCapacity(bestSources.size());
+    std::sort(bestSources.begin(), bestSources.end(), sortBasedOnFitnessScore);
+    for (auto&amp; device : bestSources)
+        sourceUIDs.uncheckedAppend(device-&gt;persistentID());
+
+    return sourceUIDs;
+}
+
+RealtimeMediaSource::CaptureFactory* RealtimeMediaSourceCenterMac::defaultAudioFactory()
+{
+    return &amp;AVAudioCaptureSource::factory();
+}
+
+RealtimeMediaSource::CaptureFactory* RealtimeMediaSourceCenterMac::defaultVideoFactory()
+{
+    return &amp;AVVideoCaptureSource::factory();
+}
+
</ins><span class="cx"> } // namespace WebCore
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(MEDIA_STREAM)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmediastreammacRealtimeMediaSourceCenterMach"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mediastream/mac/RealtimeMediaSourceCenterMac.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -50,6 +50,11 @@
</span><span class="cx">     void validateRequestConstraints(ValidConstraintsHandler validHandler, InvalidConstraintsHandler invalidHandler, const MediaConstraints&amp; audioConstraints, const MediaConstraints&amp; videoConstraints) final;
</span><span class="cx">     void createMediaStream(NewMediaStreamHandler, const String&amp; audioDeviceID, const String&amp; videoDeviceID, const MediaConstraints* audioConstraints, const MediaConstraints* videoConstraints) final;
</span><span class="cx">     Vector&lt;CaptureDevice&gt; getMediaStreamDevices() final;
</span><ins>+
+    Vector&lt;String&gt; bestSourcesForTypeAndConstraints(RealtimeMediaSource::Type, const MediaConstraints&amp;, String&amp; invalidConstraint);
+
+    RealtimeMediaSource::CaptureFactory* defaultAudioFactory() final;
+    RealtimeMediaSource::CaptureFactory* defaultVideoFactory() final;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> } // namespace WebCore
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeAudioSourcecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.cpp (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.cpp        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.cpp        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -32,6 +32,7 @@
</span><span class="cx"> #include &quot;MockRealtimeAudioSource.h&quot;
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(MEDIA_STREAM)
</span><ins>+#include &quot;CaptureDevice.h&quot;
</ins><span class="cx"> #include &quot;Logging.h&quot;
</span><span class="cx"> #include &quot;MediaConstraints.h&quot;
</span><span class="cx"> #include &quot;NotImplemented.h&quot;
</span><span class="lines">@@ -40,6 +41,15 @@
</span><span class="cx"> 
</span><span class="cx"> namespace WebCore {
</span><span class="cx"> 
</span><ins>+class MockRealtimeAudioSourceFactory : public RealtimeMediaSource::CaptureFactory {
+public:
+    RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp; captureDevice, const MediaConstraints* constraints, String&amp;) final {
+        if (captureDevice.type() == CaptureDevice::DeviceType::Audio)
+            return MockRealtimeAudioSource::create(captureDevice.label(), constraints);
+        return nullptr;
+    }
+};
+
</ins><span class="cx"> #if !PLATFORM(MAC) &amp;&amp; !PLATFORM(IOS)
</span><span class="cx"> RefPtr&lt;MockRealtimeAudioSource&gt; MockRealtimeAudioSource::create(const String&amp; name, const MediaConstraints* constraints)
</span><span class="cx"> {
</span><span class="lines">@@ -57,7 +67,13 @@
</span><span class="cx">     return source;
</span><span class="cx"> }
</span><span class="cx"> #endif
</span><del>-    
</del><ins>+
+RealtimeMediaSource::CaptureFactory&amp; MockRealtimeAudioSource::factory()
+{
+    NeverDestroyed&lt;MockRealtimeAudioSourceFactory&gt; factory;
+    return factory.get();
+}
+
</ins><span class="cx"> MockRealtimeAudioSource::MockRealtimeAudioSource(const String&amp; name)
</span><span class="cx">     : MockRealtimeMediaSource(createCanonicalUUIDString(), RealtimeMediaSource::Type::Audio, name)
</span><span class="cx">     , m_timer(RunLoop::current(), this, &amp;MockRealtimeAudioSource::tick)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeAudioSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeAudioSource.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -45,6 +45,8 @@
</span><span class="cx">     static RefPtr&lt;MockRealtimeAudioSource&gt; create(const String&amp;, const MediaConstraints*);
</span><span class="cx">     static RefPtr&lt;MockRealtimeAudioSource&gt; createMuted(const String&amp; name);
</span><span class="cx"> 
</span><ins>+    static CaptureFactory&amp; factory();
+
</ins><span class="cx">     virtual ~MockRealtimeAudioSource() = default;
</span><span class="cx"> 
</span><span class="cx"> protected:
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeMediaSourceCentercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.cpp (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.cpp        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.cpp        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -131,6 +131,17 @@
</span><span class="cx">     return sources;
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+RealtimeMediaSource::CaptureFactory* MockRealtimeMediaSourceCenter::defaultAudioFactory()
+{
+    return &amp;MockRealtimeAudioSource::factory();
+}
+
+RealtimeMediaSource::CaptureFactory* MockRealtimeMediaSourceCenter::defaultVideoFactory()
+{
+    return &amp;MockRealtimeVideoSource::factory();
+}
+
+
</ins><span class="cx"> } // namespace WebCore
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(MEDIA_STREAM)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeMediaSourceCenterh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeMediaSourceCenter.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -44,6 +44,9 @@
</span><span class="cx">     void validateRequestConstraints(ValidConstraintsHandler validHandler, InvalidConstraintsHandler invalidHandler, const MediaConstraints&amp; audioConstraints, const MediaConstraints&amp; videoConstraints) final;
</span><span class="cx">     Vector&lt;CaptureDevice&gt; getMediaStreamDevices() final;
</span><span class="cx">     void createMediaStream(NewMediaStreamHandler, const String&amp; audioDeviceID, const String&amp; videoDeviceID, const MediaConstraints* audioConstraints, const MediaConstraints* videoConstraints) final;
</span><ins>+
+    RealtimeMediaSource::CaptureFactory* defaultAudioFactory() final;
+    RealtimeMediaSource::CaptureFactory* defaultVideoFactory() final;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> }
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeVideoSourcecpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.cpp (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.cpp        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.cpp        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -32,6 +32,7 @@
</span><span class="cx"> #include &quot;MockRealtimeVideoSource.h&quot;
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(MEDIA_STREAM)
</span><ins>+#include &quot;CaptureDevice.h&quot;
</ins><span class="cx"> #include &quot;GraphicsContext.h&quot;
</span><span class="cx"> #include &quot;ImageBuffer.h&quot;
</span><span class="cx"> #include &quot;IntRect.h&quot;
</span><span class="lines">@@ -47,6 +48,15 @@
</span><span class="cx"> 
</span><span class="cx"> namespace WebCore {
</span><span class="cx"> 
</span><ins>+class MockRealtimeVideoSourceFactory : public RealtimeMediaSource::CaptureFactory {
+public:
+    RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp; captureDevice, const MediaConstraints* constraints, String&amp;) final {
+        if (captureDevice.type() == CaptureDevice::DeviceType::Video)
+            return MockRealtimeVideoSource::create(captureDevice.label(), constraints);
+        return nullptr;
+    }
+};
+
</ins><span class="cx"> #if !PLATFORM(MAC) &amp;&amp; !PLATFORM(IOS)
</span><span class="cx"> RefPtr&lt;MockRealtimeVideoSource&gt; MockRealtimeVideoSource::create(const String&amp; name, const MediaConstraints* constraints)
</span><span class="cx"> {
</span><span class="lines">@@ -65,6 +75,12 @@
</span><span class="cx"> }
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><ins>+RealtimeMediaSource::CaptureFactory&amp; MockRealtimeVideoSource::factory()
+{
+    NeverDestroyed&lt;MockRealtimeVideoSourceFactory&gt; factory;
+    return factory.get();
+}
+
</ins><span class="cx"> MockRealtimeVideoSource::MockRealtimeVideoSource(const String&amp; name)
</span><span class="cx">     : MockRealtimeMediaSource(createCanonicalUUIDString(), RealtimeMediaSource::Type::Video, name)
</span><span class="cx">     , m_timer(RunLoop::current(), this, &amp;MockRealtimeVideoSource::generateFrame)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmockMockRealtimeVideoSourceh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebCore/platform/mock/MockRealtimeVideoSource.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -49,6 +49,8 @@
</span><span class="cx">     static RefPtr&lt;MockRealtimeVideoSource&gt; create(const String&amp;, const MediaConstraints*);
</span><span class="cx">     static RefPtr&lt;MockRealtimeVideoSource&gt; createMuted(const String&amp; name);
</span><span class="cx"> 
</span><ins>+    static CaptureFactory&amp; factory();
+
</ins><span class="cx">     virtual ~MockRealtimeVideoSource() { }
</span><span class="cx"> 
</span><span class="cx"> protected:
</span></span></pre></div>
<a id="trunkSourceWebKit2ChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/ChangeLog (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/ChangeLog        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebKit2/ChangeLog        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -1,3 +1,18 @@
</span><ins>+2017-03-06  Jer Noble  &lt;jer.noble@apple.com&gt;
+
+        Refactor: Allow WebKit2 to override the creation of RealtimeMediaSources
+        https://bugs.webkit.org/show_bug.cgi?id=169227
+
+        Reviewed by Eric Carlson.
+
+        * WebKit2.xcodeproj/project.pbxproj:
+        * WebProcess/WebCoreSupport/WebUserMediaClient.cpp:
+        (WebKit::WebUserMediaClient::WebUserMediaClient):
+        (WebKit::WebUserMediaClient::initializeFactories): Add empty non-Cocoa implementation.
+        * WebProcess/WebCoreSupport/WebUserMediaClient.h:
+        * WebProcess/WebCoreSupport/cocoa/WebUserMediaClientMac.mm: Added.
+        (WebKit::WebUserMediaClient::initializeFactories): Initialize a (for now) pass-through factory.
+
</ins><span class="cx"> 2017-03-14  Dean Jackson  &lt;dino@apple.com&gt;
</span><span class="cx"> 
</span><span class="cx">         Rename LayerTypeWebGLLayer and use it for both WebGL and WebGPU
</span></span></pre></div>
<a id="trunkSourceWebKit2WebKit2xcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -1883,6 +1883,7 @@
</span><span class="cx">                 CD4B4D9D1E765E0000D27092 /* SharedRingBufferStorage.h in Headers */ = {isa = PBXBuildFile; fileRef = CD4B4D9B1E765E0000D27092 /* SharedRingBufferStorage.h */; };
</span><span class="cx">                 CD5C66A0134B9D38004FE2A8 /* InjectedBundlePageFullScreenClient.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD5C669E134B9D36004FE2A8 /* InjectedBundlePageFullScreenClient.cpp */; };
</span><span class="cx">                 CD5C66A1134B9D38004FE2A8 /* InjectedBundlePageFullScreenClient.h in Headers */ = {isa = PBXBuildFile; fileRef = CD5C669F134B9D37004FE2A8 /* InjectedBundlePageFullScreenClient.h */; };
</span><ins>+                CD6178141E6DE9A000FDA57D /* WebUserMediaClientMac.mm in Sources */ = {isa = PBXBuildFile; fileRef = CD6178121E6DE9A000FDA57D /* WebUserMediaClientMac.mm */; };
</ins><span class="cx">                 CD6F75F4131B66D000D6B21E /* WebFullScreenManagerProxy.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD73BA3E131A2E8A00EEDED2 /* WebFullScreenManagerProxy.cpp */; };
</span><span class="cx">                 CD73BA47131ACC9A00EEDED2 /* WebFullScreenManagerProxyMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD73BA45131ACC8800EEDED2 /* WebFullScreenManagerProxyMessageReceiver.cpp */; };
</span><span class="cx">                 CD73BA4E131ACDB700EEDED2 /* WebFullScreenManagerMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD73BA48131ACD8E00EEDED2 /* WebFullScreenManagerMessageReceiver.cpp */; };
</span><span class="lines">@@ -4172,6 +4173,7 @@
</span><span class="cx">                 CD4B4D9B1E765E0000D27092 /* SharedRingBufferStorage.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = SharedRingBufferStorage.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 CD5C669E134B9D36004FE2A8 /* InjectedBundlePageFullScreenClient.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = InjectedBundlePageFullScreenClient.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 CD5C669F134B9D37004FE2A8 /* InjectedBundlePageFullScreenClient.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = InjectedBundlePageFullScreenClient.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><ins>+                CD6178121E6DE9A000FDA57D /* WebUserMediaClientMac.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = WebUserMediaClientMac.mm; path = cocoa/WebUserMediaClientMac.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
</ins><span class="cx">                 CD73BA37131A29FE00EEDED2 /* WebFullScreenManager.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = WebFullScreenManager.cpp; path = FullScreen/WebFullScreenManager.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 CD73BA38131A29FE00EEDED2 /* WebFullScreenManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = WebFullScreenManager.h; path = FullScreen/WebFullScreenManager.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 CD73BA39131A29FE00EEDED2 /* WebFullScreenManager.messages.in */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; name = WebFullScreenManager.messages.in; path = FullScreen/WebFullScreenManager.messages.in; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="lines">@@ -6450,6 +6452,7 @@
</span><span class="cx">                 BC032D5D10F437220058C15A /* WebCoreSupport */ = {
</span><span class="cx">                         isa = PBXGroup;
</span><span class="cx">                         children = (
</span><ins>+                                CD6178111E6DE98000FDA57D /* cocoa */,
</ins><span class="cx">                                 2D28F3DF1885CCB4004B9EAE /* ios */,
</span><span class="cx">                                 BC111ADE112F5B9A00337BAB /* mac */,
</span><span class="cx">                                 1A7284441959ED100007BCE5 /* SessionStateConversion.cpp */,
</span><span class="lines">@@ -7818,6 +7821,14 @@
</span><span class="cx">                         name = forms;
</span><span class="cx">                         sourceTree = &quot;&lt;group&gt;&quot;;
</span><span class="cx">                 };
</span><ins>+                CD6178111E6DE98000FDA57D /* cocoa */ = {
+                        isa = PBXGroup;
+                        children = (
+                                CD6178121E6DE9A000FDA57D /* WebUserMediaClientMac.mm */,
+                        );
+                        name = cocoa;
+                        sourceTree = &quot;&lt;group&gt;&quot;;
+                };
</ins><span class="cx">                 CD73BA3D131A2A2100EEDED2 /* FullScreen */ = {
</span><span class="cx">                         isa = PBXGroup;
</span><span class="cx">                         children = (
</span><span class="lines">@@ -9968,6 +9979,7 @@
</span><span class="cx">                                 753E3E0D1887398500188496 /* SessionTracker.cpp in Sources */,
</span><span class="cx">                                 1A6420E412DCE2FF00CAAE2C /* ShareableBitmap.cpp in Sources */,
</span><span class="cx">                                 C01A260112662F2100C9ED55 /* ShareableBitmapCG.cpp in Sources */,
</span><ins>+                                CD6178141E6DE9A000FDA57D /* WebUserMediaClientMac.mm in Sources */,
</ins><span class="cx">                                 51217460164C20E30037A5C1 /* ShareableResource.cpp in Sources */,
</span><span class="cx">                                 4450AEC01DC3FAE5009943F2 /* SharedMemoryCocoa.cpp in Sources */,
</span><span class="cx">                                 2DAF06D718BD1A470081CEB1 /* SmartMagnificationController.mm in Sources */,
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessWebCoreSupportWebUserMediaClientcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.cpp (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.cpp        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.cpp        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -33,6 +33,7 @@
</span><span class="cx"> WebUserMediaClient::WebUserMediaClient(WebPage&amp; page)
</span><span class="cx">     : m_page(page)
</span><span class="cx"> {
</span><ins>+    initializeFactories();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void WebUserMediaClient::pageDestroyed()
</span><span class="lines">@@ -60,6 +61,13 @@
</span><span class="cx">     m_page.userMediaPermissionRequestManager().cancelMediaDevicesEnumeration(request);
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+#if !PLATFORM(COCOA)
+void WebUserMediaClient::initializeFactories()
+{
+
+}
+#endif
+
</ins><span class="cx"> } // namespace WebKit;
</span><span class="cx"> 
</span><span class="cx"> #endif // MEDIA_STREAM
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessWebCoreSupportWebUserMediaClienth"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.h (213940 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.h        2017-03-14 21:39:22 UTC (rev 213940)
+++ trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebUserMediaClient.h        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -42,6 +42,8 @@
</span><span class="cx">     void enumerateMediaDevices(WebCore::MediaDevicesEnumerationRequest&amp;) final;
</span><span class="cx">     void cancelMediaDevicesEnumerationRequest(WebCore::MediaDevicesEnumerationRequest&amp;) final;
</span><span class="cx"> 
</span><ins>+    void initializeFactories();
+
</ins><span class="cx">     WebPage&amp; m_page;
</span><span class="cx"> };
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessWebCoreSupportcocoaWebUserMediaClientMacmm"></a>
<div class="addfile"><h4>Added: trunk/Source/WebKit2/WebProcess/WebCoreSupport/cocoa/WebUserMediaClientMac.mm (0 => 213941)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/WebCoreSupport/cocoa/WebUserMediaClientMac.mm                                (rev 0)
+++ trunk/Source/WebKit2/WebProcess/WebCoreSupport/cocoa/WebUserMediaClientMac.mm        2017-03-14 21:41:48 UTC (rev 213941)
</span><span class="lines">@@ -0,0 +1,63 @@
</span><ins>+/*
+ * Copyright (C) 2017 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.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS 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 APPLE INC. OR ITS 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.
+ */
+
+#include &quot;config.h&quot;
+#include &quot;WebUserMediaClient.h&quot;
+
+#if ENABLE(MEDIA_STREAM) &amp;&amp; PLATFORM(COCOA)
+
+#import &lt;WebCore/RealtimeMediaSourceCenter.h&gt;
+#import &lt;wtf/NeverDestroyed.h&gt;
+
+using namespace WebCore;
+
+namespace WebKit {
+
+class WebUserMediaClientAudioFactory final : public RealtimeMediaSource::CaptureFactory {
+public:
+    static WebUserMediaClientAudioFactory&amp; singleton()
+    {
+        static NeverDestroyed&lt;WebUserMediaClientAudioFactory&gt; factory;
+        return factory;
+    }
+
+private:
+    RefPtr&lt;RealtimeMediaSource&gt; createMediaSourceForCaptureDeviceWithConstraints(const CaptureDevice&amp; device, const MediaConstraints* constraints, String&amp; invalidConstraints) final {
+        auto* factory = RealtimeMediaSourceCenter::singleton().defaultAudioFactory();
+        return factory ? factory-&gt;createMediaSourceForCaptureDeviceWithConstraints(device, constraints, invalidConstraints) : nullptr;
+    }
+};
+
+void WebUserMediaClient::initializeFactories()
+{
+    static dispatch_once_t onceToken;
+    dispatch_once(&amp;onceToken, ^ {
+        WebCore::RealtimeMediaSourceCenter::singleton().setAudioFactory(WebUserMediaClientAudioFactory::singleton());
+    });
+}
+
+}
+
+#endif
</ins></span></pre>
</div>
</div>

</body>
</html>