Index: Source/core/html/HTMLMediaElement.cpp |
diff --git a/Source/core/html/HTMLMediaElement.cpp b/Source/core/html/HTMLMediaElement.cpp |
index 2a8bc6b446321e6740ccabdf0c2f7afa8509fcaa..2c05d87d7e23e31d0179962a0750e3bfddab399f 100644 |
--- a/Source/core/html/HTMLMediaElement.cpp |
+++ b/Source/core/html/HTMLMediaElement.cpp |
@@ -324,6 +324,7 @@ HTMLMediaElement::HTMLMediaElement(const QualifiedName& tagName, Document& docum |
, m_duration(std::numeric_limits<double>::quiet_NaN()) |
, m_lastTimeUpdateEventWallTime(0) |
, m_lastTimeUpdateEventMovieTime(std::numeric_limits<double>::max()) |
+ , m_defaultPlaybackStartPosition(0) |
, m_loadState(WaitingForSource) |
, m_deferredLoadState(NotDeferred) |
, m_deferredLoadTimer(this, &HTMLMediaElement::deferredLoadTimerFired) |
@@ -1817,6 +1818,12 @@ void HTMLMediaElement::setReadyState(ReadyState state) |
if (isHTMLVideoElement()) |
scheduleEvent(EventTypeNames::resize); |
scheduleEvent(EventTypeNames::loadedmetadata); |
+ |
+ if (m_defaultPlaybackStartPosition > 0) { |
+ seek(m_defaultPlaybackStartPosition); |
+ m_defaultPlaybackStartPosition = 0; |
philipj_slow
2014/09/10 09:57:05
Either move this out of the if clause, like the sp
amogh.bihani
2014/09/10 11:18:33
Done.
|
+ } |
+ |
if (hasMediaControls()) |
mediaControls()->reset(); |
if (renderer()) |
@@ -1917,17 +1924,15 @@ void HTMLMediaElement::prepareToPlay() |
startDeferredLoad(); |
} |
-void HTMLMediaElement::seek(double time, ExceptionState& exceptionState) |
+void HTMLMediaElement::seek(double time) |
{ |
WTF_LOG(Media, "HTMLMediaElement::seek(%p, %f)", this, time); |
- // 4.8.10.9 Seeking |
+ // 4.7.14.9 Seeking |
philipj_slow
2014/09/10 09:57:05
Now it's "4.8.14.9 Seeking" in the spec. The secti
amogh.bihani
2014/09/10 11:18:33
Done.
|
- // 1 - If the media element's readyState is HAVE_NOTHING, then raise an InvalidStateError exception. |
- if (m_readyState == HAVE_NOTHING) { |
- exceptionState.throwDOMException(InvalidStateError, "The element's readyState is HAVE_NOTHING."); |
+ // 2 - If the media element's readyState is HAVE_NOTHING, abort these steps. |
+ if (m_readyState == HAVE_NOTHING) |
return; |
- } |
// If the media engine has been told to postpone loading data, let it go ahead now. |
if (m_preload < MediaPlayer::Auto && m_readyState < HAVE_FUTURE_DATA) |
@@ -1935,23 +1940,24 @@ void HTMLMediaElement::seek(double time, ExceptionState& exceptionState) |
// Get the current time before setting m_seeking, m_lastSeekTime is returned once it is set. |
refreshCachedTime(); |
- double now = currentTime(); |
+ // This is needed to avoid getting default playback start position from currentTime(). |
+ double now = m_cachedTime; |
- // 2 - If the element's seeking IDL attribute is true, then another instance of this algorithm is |
+ // 3 - If the element's seeking IDL attribute is true, then another instance of this algorithm is |
// already running. Abort that other instance of the algorithm without waiting for the step that |
// it is running to complete. |
// Nothing specific to be done here. |
- // 3 - Set the seeking IDL attribute to true. |
+ // 4 - Set the seeking IDL attribute to true. |
// The flag will be cleared when the engine tells us the time has actually changed. |
bool previousSeekStillPending = m_seeking; |
m_seeking = true; |
- // 5 - If the new playback position is later than the end of the media resource, then let it be the end |
+ // 6 - If the new playback position is later than the end of the media resource, then let it be the end |
// of the media resource instead. |
time = std::min(time, duration()); |
- // 6 - If the new playback position is less than the earliest possible position, let it be that position instead. |
+ // 7 - If the new playback position is less than the earliest possible position, let it be that position instead. |
time = std::max(time, 0.0); |
// Ask the media engine for the time value in the movie's time scale before comparing with current time. This |
@@ -1965,7 +1971,7 @@ void HTMLMediaElement::seek(double time, ExceptionState& exceptionState) |
time = mediaTime; |
} |
- // 7 - If the (possibly now changed) new playback position is not in one of the ranges given in the |
+ // 8 - If the (possibly now changed) new playback position is not in one of the ranges given in the |
// seekable attribute, then let it be the position in one of the ranges given in the seekable attribute |
// that is the nearest to the new playback position. ... If there are no ranges given in the seekable |
// attribute then set the seeking IDL attribute to false and abort these steps. |
@@ -1998,13 +2004,13 @@ void HTMLMediaElement::seek(double time, ExceptionState& exceptionState) |
m_lastSeekTime = time; |
m_sentEndEvent = false; |
- // 8 - Queue a task to fire a simple event named seeking at the element. |
+ // 10 - Queue a task to fire a simple event named seeking at the element. |
scheduleEvent(EventTypeNames::seeking); |
- // 9 - Set the current playback position to the given new playback position |
+ // 11 - Set the current playback position to the given new playback position |
philipj_slow
2014/09/10 09:57:06
Can you add the missing period here?
amogh.bihani
2014/09/10 11:18:33
Done.
|
webMediaPlayer()->seek(time); |
- // 10-14 are handled, if necessary, when the engine signals a readystate change or otherwise |
+ // 12-17 are handled, if necessary, when the engine signals a readystate change or otherwise |
philipj_slow
2014/09/10 09:57:06
It's step 14-17 that's handled in finishSeek(). Ca
amogh.bihani
2014/09/10 11:18:33
Done.
|
// satisfies seek completion and signals a time change. |
} |
@@ -2057,6 +2063,9 @@ void HTMLMediaElement::invalidateCachedTime() |
// playback state |
double HTMLMediaElement::currentTime() const |
{ |
+ if (m_defaultPlaybackStartPosition) |
+ return m_defaultPlaybackStartPosition; |
+ |
if (m_readyState == HAVE_NOTHING) |
return 0; |
@@ -2086,7 +2095,15 @@ void HTMLMediaElement::setCurrentTime(double time, ExceptionState& exceptionStat |
exceptionState.throwDOMException(InvalidStateError, "The element is slaved to a MediaController."); |
return; |
} |
- seek(time, exceptionState); |
+ |
+ // If the media element's readyState is HAVE_NOTHING, then set the default |
+ // playback start position to that time. |
+ if (m_readyState == HAVE_NOTHING) { |
+ m_defaultPlaybackStartPosition = time; |
+ return; |
+ } |
+ |
+ seek(time); |
} |
double HTMLMediaElement::duration() const |
@@ -2225,7 +2242,7 @@ void HTMLMediaElement::playInternal() |
scheduleDelayedAction(LoadMediaResource); |
if (endedPlayback()) |
- seek(0, IGNORE_EXCEPTION); |
+ seek(0); |
if (m_mediaController) |
m_mediaController->bringElementUpToSpeed(this); |
@@ -3083,7 +3100,7 @@ void HTMLMediaElement::mediaPlayerTimeChanged() |
if (loop() && !m_mediaController) { |
m_sentEndEvent = false; |
// then seek to the earliest possible position of the media resource and abort these steps. |
- seek(0, IGNORE_EXCEPTION); |
+ seek(0); |
} else { |
// If the media element does not have a current media controller, and the media element |
// has still ended playback, and the direction of playback is still forwards, and paused |
@@ -3137,7 +3154,7 @@ void HTMLMediaElement::durationChanged(double duration, bool requestSeek) |
renderer()->updateFromElement(); |
if (requestSeek) |
- seek(duration, IGNORE_EXCEPTION); |
+ seek(duration); |
} |
void HTMLMediaElement::mediaPlayerPlaybackStateChanged() |
@@ -3168,10 +3185,10 @@ void HTMLMediaElement::mediaPlayerRequestSeek(double time) |
{ |
// The player is the source of this seek request. |
if (m_mediaController) { |
- m_mediaController->setCurrentTime(time, IGNORE_EXCEPTION); |
+ m_mediaController->setCurrentTime(time); |
return; |
} |
- setCurrentTime(time, IGNORE_EXCEPTION); |
+ setCurrentTime(time, ASSERT_NO_EXCEPTION); |
} |
// MediaPlayerPresentation methods |
@@ -3870,7 +3887,7 @@ void HTMLMediaElement::applyMediaFragmentURI() |
if (m_fragmentStartTime != MediaPlayer::invalidTime()) { |
m_sentEndEvent = false; |
UseCounter::count(document(), UseCounter::HTMLMediaElementSeekToFragmentStart); |
- seek(m_fragmentStartTime, IGNORE_EXCEPTION); |
+ seek(m_fragmentStartTime); |
} |
} |