| Index: Source/core/html/HTMLMediaElement.cpp
|
| diff --git a/Source/core/html/HTMLMediaElement.cpp b/Source/core/html/HTMLMediaElement.cpp
|
| index 91ef6708e6f5e78594ef9b36ad751aec9955cc39..7091070161a06ee81ebe6d13c4a33a10d2ec2d6c 100644
|
| --- a/Source/core/html/HTMLMediaElement.cpp
|
| +++ b/Source/core/html/HTMLMediaElement.cpp
|
| @@ -48,6 +48,7 @@
|
| #include "core/html/MediaController.h"
|
| #include "core/html/MediaError.h"
|
| #include "core/html/MediaFragmentURIParser.h"
|
| +#include "core/html/MediaProvider.h"
|
| #include "core/html/TimeRanges.h"
|
| #include "core/html/shadow/MediaControls.h"
|
| #include "core/html/track/AudioTrack.h"
|
| @@ -325,6 +326,7 @@ HTMLMediaElement::HTMLMediaElement(const QualifiedName& tagName, Document& docum
|
| , m_lastTimeUpdateEventWallTime(0)
|
| , m_lastTimeUpdateEventMovieTime(std::numeric_limits<double>::max())
|
| , m_loadState(WaitingForSource)
|
| + , m_srcObject(std::nullptr_t())
|
| , m_deferredLoadState(NotDeferred)
|
| , m_deferredLoadTimer(this, &HTMLMediaElement::deferredLoadTimerFired)
|
| , m_webLayer(0)
|
| @@ -682,6 +684,19 @@ PassRefPtrWillBeRawPtr<MediaError> HTMLMediaElement::error() const
|
| return m_error;
|
| }
|
|
|
| +void HTMLMediaElement::setSrcObject(RawPtr<MediaProvider> mediaProvider)
|
| +{
|
| + WTF_LOG(Media, "HTMLMediaElement::setSrcObject()");
|
| + m_srcObject = mediaProvider;
|
| + clearMediaPlayer(LoadMediaResource);
|
| + scheduleDelayedAction(LoadMediaResource);
|
| +}
|
| +
|
| +MediaProvider* HTMLMediaElement::srcObject() const
|
| +{
|
| + return m_srcObject.get();
|
| +}
|
| +
|
| void HTMLMediaElement::setSrc(const AtomicString& url)
|
| {
|
| setAttribute(srcAttr, url);
|
| @@ -855,29 +870,32 @@ void HTMLMediaElement::selectMediaResource()
|
| {
|
| WTF_LOG(Media, "HTMLMediaElement::selectMediaResource");
|
|
|
| - enum Mode { attribute, children };
|
| -
|
| - // 3 - If the media element has a src attribute, then let mode be attribute.
|
| - Mode mode = attribute;
|
| - if (!fastHasAttribute(srcAttr)) {
|
| - // Otherwise, if the media element does not have a src attribute but has a source
|
| - // element child, then let mode be children and let candidate be the first such
|
| - // source element child in tree order.
|
| - if (HTMLSourceElement* element = Traversal<HTMLSourceElement>::firstChild(*this)) {
|
| - mode = children;
|
| - m_nextChildNodeToConsider = element;
|
| - m_currentSourceNode = nullptr;
|
| - } else {
|
| - // Otherwise the media element has neither a src attribute nor a source element
|
| - // child: set the networkState to NETWORK_EMPTY, and abort these steps; the
|
| - // synchronous section ends.
|
| - m_loadState = WaitingForSource;
|
| - setShouldDelayLoadEvent(false);
|
| - m_networkState = NETWORK_EMPTY;
|
| + enum Mode {Object, Attribute, Children};
|
| +
|
| + // 3 - Decide which source to load.
|
| + // If the media element has a srcObject let the mode be object.
|
| + // If it has a src attribute, let the mode be attribute.
|
| + // If it has a source element, let the mode be Children.
|
| + Mode mode = Object;
|
| + if (srcObject()) {
|
| + mode = Object;
|
| + } else if (fastHasAttribute(srcAttr)) {
|
| + mode = Attribute;
|
| + } else if (Traversal<HTMLSourceElement>::firstChild(*this)) {
|
| + mode = Children;
|
| + HTMLSourceElement* element = Traversal<HTMLSourceElement>::firstChild(*this);
|
| + m_nextChildNodeToConsider = element;
|
| + m_currentSourceNode = nullptr;
|
| + } else {
|
| + // Otherwise the media element has no source.
|
| + // set the networkState to NETWORK_EMPTY, and abort these steps; the
|
| + // synchronous section ends.
|
| + m_loadState = WaitingForSource;
|
| + setShouldDelayLoadEvent(false);
|
| + m_networkState = NETWORK_EMPTY;
|
|
|
| - WTF_LOG(Media, "HTMLMediaElement::selectMediaResource, nothing to load");
|
| - return;
|
| - }
|
| + WTF_LOG(Media, "HTMLMediaElement::selectMediaResource, nothing to load");
|
| + return;
|
| }
|
|
|
| // 4 - Set the media element's delaying-the-load-event flag to true (this delays the load event),
|
| @@ -888,34 +906,64 @@ void HTMLMediaElement::selectMediaResource()
|
| // 5 - Queue a task to fire a simple event named loadstart at the media element.
|
| scheduleEvent(EventTypeNames::loadstart);
|
|
|
| - // 6 - If mode is attribute, then run these substeps
|
| - if (mode == attribute) {
|
| - m_loadState = LoadingFromSrcAttr;
|
| + // 6 - Load the correct source.
|
| + switch (mode) {
|
| + case Object:
|
| + loadSourceFromObject();
|
| + break;
|
| + case Attribute:
|
| + loadSourceFromAttribute();
|
| + break;
|
| + case Children:
|
| + loadNextSourceChild();
|
| + break;
|
| + }
|
| +}
|
| +
|
| +void HTMLMediaElement::loadSourceFromObject()
|
| +{
|
| + m_loadState = LoadingFromSrcObject;
|
|
|
| - // If the src attribute's value is the empty string ... jump down to the failed step below
|
| - KURL mediaURL = getNonEmptyURLAttribute(srcAttr);
|
| - if (mediaURL.isEmpty()) {
|
| - mediaLoadingFailed(WebMediaPlayer::NetworkStateFormatError);
|
| - WTF_LOG(Media, "HTMLMediaElement::selectMediaResource, empty 'src'");
|
| - return;
|
| - }
|
| + KURL mediaURL = document().completeURL(m_srcObject->getObjectUrl());
|
|
|
| - if (!isSafeToLoadURL(mediaURL, Complain)) {
|
| - mediaLoadingFailed(WebMediaPlayer::NetworkStateFormatError);
|
| - return;
|
| - }
|
| + if (!isSafeToLoadURL(mediaURL, Complain)) {
|
| + mediaLoadingFailed(WebMediaPlayer::NetworkStateFormatError);
|
| + return;
|
| + }
|
| +
|
| + // No type or key system information is available when the url comes
|
| + // from the 'srcObject' so MediaPlayer
|
| + // will have to pick a media engine based on the file extension.
|
| + ContentType contentType((String()));
|
| + loadResource(mediaURL, contentType, String());
|
| + WTF_LOG(Media, "HTMLMediaElement::selectMediaResource, using 'srcObject' attribute.");
|
| + return;
|
| +}
|
| +
|
| +void HTMLMediaElement::loadSourceFromAttribute()
|
| +{
|
| + m_loadState = LoadingFromSrcAttr;
|
| +
|
| + // If the src attribute's value is the empty string ... jump down to the failed step below
|
| + KURL mediaURL = getNonEmptyURLAttribute(srcAttr);
|
| + if (mediaURL.isEmpty()) {
|
| + mediaLoadingFailed(WebMediaPlayer::NetworkStateFormatError);
|
| + WTF_LOG(Media, "HTMLMediaElement::selectMediaResource, empty 'src'");
|
| + return;
|
| + }
|
|
|
| - // No type or key system information is available when the url comes
|
| - // from the 'src' attribute so MediaPlayer
|
| - // will have to pick a media engine based on the file extension.
|
| - ContentType contentType((String()));
|
| - loadResource(mediaURL, contentType, String());
|
| - WTF_LOG(Media, "HTMLMediaElement::selectMediaResource, using 'src' attribute url");
|
| + if (!isSafeToLoadURL(mediaURL, Complain)) {
|
| + mediaLoadingFailed(WebMediaPlayer::NetworkStateFormatError);
|
| return;
|
| }
|
|
|
| - // Otherwise, the source elements will be used
|
| - loadNextSourceChild();
|
| + // No type or key system information is available when the url comes
|
| + // from the 'src' attribute so MediaPlayer
|
| + // will have to pick a media engine based on the file extension.
|
| + ContentType contentType((String()));
|
| + loadResource(mediaURL, contentType, String());
|
| + WTF_LOG(Media, "HTMLMediaElement::selectMediaResource, using 'src' attribute url");
|
| + return;
|
| }
|
|
|
| void HTMLMediaElement::loadNextSourceChild()
|
|
|