summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYoann Lopes <yoann.lopes@digia.com>2014-04-04 15:09:03 +0200
committerThe Qt Project <gerrit-noreply@qt-project.org>2014-04-08 18:50:02 +0200
commit08216062609dea47e78046dc0eeb12bc1ea8e49a (patch)
tree0a7595a51203793ee3c50fcd4a00797ccb2e93d9
parent6fb0d978389f3f578ce43ddeb6a1bad624df4154 (diff)
downloadqtmultimedia-08216062609dea47e78046dc0eeb12bc1ea8e49a.tar.gz
WMF: more reliable video seeking.
When seeking, the presentation clock can enter an undefined state until it is started again from the new position. Wait for the clock to be restarted before scheduling the prerolled frames, otherwise these frames might get a wrong presentation time. Change-Id: I02cb3338239775b7ef5d206ec5aa1b26719ac978 Reviewed-by: Christian Stromme <christian.stromme@digia.com>
-rw-r--r--src/plugins/wmf/player/mfvideorenderercontrol.cpp25
1 files changed, 15 insertions, 10 deletions
diff --git a/src/plugins/wmf/player/mfvideorenderercontrol.cpp b/src/plugins/wmf/player/mfvideorenderercontrol.cpp
index d4d341a45..040682965 100644
--- a/src/plugins/wmf/player/mfvideorenderercontrol.cpp
+++ b/src/plugins/wmf/player/mfvideorenderercontrol.cpp
@@ -655,11 +655,6 @@ namespace
m_presentationClock = NULL;
}
- if (m_scheduledBuffer) {
- m_scheduledBuffer->Release();
- m_scheduledBuffer = NULL;
- }
-
clearMediaTypes();
clearSampleQueue();
clearBufferCache();
@@ -677,6 +672,7 @@ namespace
QMutexLocker locker(&m_mutex);
HRESULT hr = validateOperation(OpPreroll);
if (SUCCEEDED(hr)) {
+ m_state = State_Prerolling;
m_prerollTargetTime = hnsUpcomingStartTime;
hr = queueAsyncOperation(OpPreroll);
}
@@ -864,6 +860,7 @@ namespace
if (m_scheduledBuffer) {
m_scheduledBuffer->Release();
m_scheduledBuffer = NULL;
+ schedulePresentation(true);
}
}
@@ -936,6 +933,7 @@ namespace
{
State_TypeNotSet = 0, // No media type is set
State_Ready, // Media type is set, Start has never been called.
+ State_Prerolling,
State_Started,
State_Paused,
State_Stopped,
@@ -1124,6 +1122,9 @@ namespace
break;
}
}
+
+ if (m_state == State_Started)
+ schedulePresentation(true);
case OpRestart:
endPreroll(S_FALSE);
if (SUCCEEDED(hr)) {
@@ -1142,10 +1143,7 @@ namespace
case OpStop:
// Drop samples from queue.
hr = processSamplesFromQueue(DropSamples);
- if (m_scheduledBuffer) {
- m_scheduledBuffer->Release();
- m_scheduledBuffer = NULL;
- }
+ clearBufferCache();
// Send the event even if the previous call failed.
hr = queueEvent(MEStreamSinkStopped, GUID_NULL, hr, NULL);
if (m_surface->isActive()) {
@@ -1388,11 +1386,16 @@ namespace
foreach (SampleBuffer sb, m_bufferCache)
sb.m_buffer->Release();
m_bufferCache.clear();
+
+ if (m_scheduledBuffer) {
+ m_scheduledBuffer->Release();
+ m_scheduledBuffer = NULL;
+ }
}
void schedulePresentation(bool requestSample)
{
- if (m_state == State_Paused)
+ if (m_state == State_Paused || m_state == State_Prerolling)
return;
if (!m_scheduledBuffer) {
//get time from presentation time
@@ -1441,6 +1444,8 @@ namespace
/* Ready */ TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE,
+ /* Prerolling */ TRUE, TRUE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE,
+
/* Start */ FALSE, TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE,
/* Pause */ FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE,