Bug 1046003 - Ensure duplicate frames after a seek have an Image. r=kinetik

This commit is contained in:
Chris Pearce 2014-08-07 12:02:56 +12:00
parent b70ca94394
commit 52b09f9305
3 changed files with 43 additions and 1 deletions

View File

@ -158,6 +158,22 @@ VideoData* VideoData::ShallowCopyUpdateTimestamp(VideoData* aOther,
return v;
}
/* static */
VideoData* VideoData::ShallowCopyUpdateTimestampAndDuration(VideoData* aOther,
int64_t aTimestamp,
int64_t aDuration)
{
NS_ENSURE_TRUE(aOther, nullptr);
VideoData* v = new VideoData(aOther->mOffset,
aTimestamp,
aDuration,
aOther->mKeyframe,
aOther->mTimecode,
aOther->mDisplay);
v->mImage = aOther->mImage;
return v;
}
/* static */
void VideoData::SetVideoDataToImage(PlanarYCbCrImage* aVideoImage,
VideoInfo& aInfo,

View File

@ -209,6 +209,13 @@ public:
static VideoData* ShallowCopyUpdateTimestamp(VideoData* aOther,
int64_t aTimestamp);
// Creates a new VideoData identical to aOther, but with a different
// specified timestamp and duration. All data from aOther is copied
// into the new VideoData, as ShallowCopyUpdateDuration() does.
static VideoData* ShallowCopyUpdateTimestampAndDuration(VideoData* aOther,
int64_t aTimestamp,
int64_t aDuration);
// Initialize PlanarYCbCrImage. Only When aCopyData is true,
// video data is copied to PlanarYCbCrImage.
static void SetVideoDataToImage(PlanarYCbCrImage* aVideoImage,

View File

@ -2690,9 +2690,28 @@ nsresult
MediaDecoderStateMachine::DropVideoUpToSeekTarget(VideoData* aSample)
{
nsAutoPtr<VideoData> video(aSample);
MOZ_ASSERT(video);
DECODER_LOG(PR_LOG_DEBUG,
"DropVideoUpToSeekTarget() frame [%lld, %lld] dup=%d",
video->mTime, video->GetEndTime(), video->mDuplicate);
const int64_t target = mCurrentSeekTarget.mTime;
// Duplicate handling: if we're dropping frames up the seek target, we must
// be wary of Theora duplicate frames. They don't have an image, so if the
// target frame is in a run of duplicates, we won't have an image to draw
// after the seek. So store the last frame encountered while dropping, and
// copy its Image forward onto duplicate frames, so that every frame has
// an Image.
if (video->mDuplicate &&
mFirstVideoFrameAfterSeek &&
!mFirstVideoFrameAfterSeek->mDuplicate) {
VideoData* temp =
VideoData::ShallowCopyUpdateTimestampAndDuration(mFirstVideoFrameAfterSeek,
video->mTime,
video->mDuration);
video = temp;
}
// If the frame end time is less than the seek target, we won't want
// to display this frame after the seek, so discard it.
if (target >= video->GetEndTime()) {