OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "media/base/pipeline.h" | 5 #include "media/base/pipeline.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 | 8 |
9 #include "base/bind.h" | 9 #include "base/bind.h" |
10 #include "base/callback.h" | 10 #include "base/callback.h" |
(...skipping 21 matching lines...) Expand all Loading... | |
32 Pipeline::Pipeline( | 32 Pipeline::Pipeline( |
33 const scoped_refptr<base::SingleThreadTaskRunner>& task_runner, | 33 const scoped_refptr<base::SingleThreadTaskRunner>& task_runner, |
34 MediaLog* media_log) | 34 MediaLog* media_log) |
35 : task_runner_(task_runner), | 35 : task_runner_(task_runner), |
36 media_log_(media_log), | 36 media_log_(media_log), |
37 running_(false), | 37 running_(false), |
38 did_loading_progress_(false), | 38 did_loading_progress_(false), |
39 volume_(1.0f), | 39 volume_(1.0f), |
40 playback_rate_(0.0f), | 40 playback_rate_(0.0f), |
41 status_(PIPELINE_OK), | 41 status_(PIPELINE_OK), |
42 is_initialized_(false), | |
43 state_(kCreated), | 42 state_(kCreated), |
44 renderer_ended_(false), | 43 renderer_ended_(false), |
45 text_renderer_ended_(false), | 44 text_renderer_ended_(false), |
46 demuxer_(NULL), | 45 demuxer_(NULL), |
47 weak_factory_(this) { | 46 weak_factory_(this) { |
48 media_log_->AddEvent(media_log_->CreatePipelineStateChangedEvent(kCreated)); | 47 media_log_->AddEvent(media_log_->CreatePipelineStateChangedEvent(kCreated)); |
49 media_log_->AddEvent( | 48 media_log_->AddEvent( |
50 media_log_->CreateEvent(MediaLogEvent::PIPELINE_CREATED)); | 49 media_log_->CreateEvent(MediaLogEvent::PIPELINE_CREATED)); |
51 } | 50 } |
52 | 51 |
(...skipping 237 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
290 UMA_HISTOGRAM_LONG_TIMES("Media.Duration", duration); | 289 UMA_HISTOGRAM_LONG_TIMES("Media.Duration", duration); |
291 | 290 |
292 base::AutoLock auto_lock(lock_); | 291 base::AutoLock auto_lock(lock_); |
293 duration_ = duration; | 292 duration_ = duration; |
294 if (!duration_change_cb_.is_null()) | 293 if (!duration_change_cb_.is_null()) |
295 duration_change_cb_.Run(); | 294 duration_change_cb_.Run(); |
296 } | 295 } |
297 | 296 |
298 void Pipeline::OnStateTransition(PipelineStatus status) { | 297 void Pipeline::OnStateTransition(PipelineStatus status) { |
299 DCHECK(task_runner_->BelongsToCurrentThread()); | 298 DCHECK(task_runner_->BelongsToCurrentThread()); |
299 // When demuxer has finished the init segment, it should call ReportMetadata | |
DaleCurtis
2014/11/20 18:59:51
This is too general of a location for this code; t
| |
300 // in case meeting 'decode' error when passing media segment but | |
301 // WebMediaPlayer's ready_state_ is still ReadyStateHaveNothing. In that case | |
302 // it will be treated as NetworkStateFormatError not NetworkStateDecodeError. | |
303 if (state_ == kInitDemuxer && status == PIPELINE_OK) { | |
304 ReportMetadata(); | |
305 start_timestamp_ = demuxer_->GetStartTime(); | |
306 } | |
300 // Force post to process state transitions after current execution frame. | 307 // Force post to process state transitions after current execution frame. |
301 task_runner_->PostTask( | 308 task_runner_->PostTask( |
302 FROM_HERE, | 309 FROM_HERE, |
303 base::Bind( | 310 base::Bind( |
304 &Pipeline::StateTransitionTask, weak_factory_.GetWeakPtr(), status)); | 311 &Pipeline::StateTransitionTask, weak_factory_.GetWeakPtr(), status)); |
305 } | 312 } |
306 | 313 |
307 void Pipeline::StateTransitionTask(PipelineStatus status) { | 314 void Pipeline::StateTransitionTask(PipelineStatus status) { |
308 DCHECK(task_runner_->BelongsToCurrentThread()); | 315 DCHECK(task_runner_->BelongsToCurrentThread()); |
309 | 316 |
(...skipping 22 matching lines...) Expand all Loading... | |
332 // Switch states, performing any entrance actions for the new state as well. | 339 // Switch states, performing any entrance actions for the new state as well. |
333 SetState(GetNextState()); | 340 SetState(GetNextState()); |
334 switch (state_) { | 341 switch (state_) { |
335 case kInitDemuxer: | 342 case kInitDemuxer: |
336 return InitializeDemuxer(done_cb); | 343 return InitializeDemuxer(done_cb); |
337 | 344 |
338 case kInitRenderer: | 345 case kInitRenderer: |
339 return InitializeRenderer(base::Bind(done_cb, PIPELINE_OK)); | 346 return InitializeRenderer(base::Bind(done_cb, PIPELINE_OK)); |
340 | 347 |
341 case kPlaying: | 348 case kPlaying: |
342 // Report metadata the first time we enter the playing state. | |
343 if (!is_initialized_) { | |
344 is_initialized_ = true; | |
345 ReportMetadata(); | |
346 start_timestamp_ = demuxer_->GetStartTime(); | |
347 } | |
348 | |
349 base::ResetAndReturn(&seek_cb_).Run(PIPELINE_OK); | 349 base::ResetAndReturn(&seek_cb_).Run(PIPELINE_OK); |
350 | 350 |
351 DCHECK(start_timestamp_ >= base::TimeDelta()); | 351 DCHECK(start_timestamp_ >= base::TimeDelta()); |
352 renderer_->StartPlayingFrom(start_timestamp_); | 352 renderer_->StartPlayingFrom(start_timestamp_); |
353 | 353 |
354 if (text_renderer_) | 354 if (text_renderer_) |
355 text_renderer_->StartPlaying(); | 355 text_renderer_->StartPlaying(); |
356 | 356 |
357 PlaybackRateChangedTask(GetPlaybackRate()); | 357 PlaybackRateChangedTask(GetPlaybackRate()); |
358 VolumeChangedTask(GetVolume()); | 358 VolumeChangedTask(GetVolume()); |
(...skipping 336 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
695 done_cb, | 695 done_cb, |
696 base::Bind(&Pipeline::OnUpdateStatistics, weak_this), | 696 base::Bind(&Pipeline::OnUpdateStatistics, weak_this), |
697 base::Bind(&Pipeline::OnRendererEnded, weak_this), | 697 base::Bind(&Pipeline::OnRendererEnded, weak_this), |
698 base::Bind(&Pipeline::OnError, weak_this), | 698 base::Bind(&Pipeline::OnError, weak_this), |
699 base::Bind(&Pipeline::BufferingStateChanged, weak_this)); | 699 base::Bind(&Pipeline::BufferingStateChanged, weak_this)); |
700 } | 700 } |
701 | 701 |
702 void Pipeline::ReportMetadata() { | 702 void Pipeline::ReportMetadata() { |
703 DCHECK(task_runner_->BelongsToCurrentThread()); | 703 DCHECK(task_runner_->BelongsToCurrentThread()); |
704 PipelineMetadata metadata; | 704 PipelineMetadata metadata; |
705 metadata.has_audio = renderer_->HasAudio(); | |
706 metadata.has_video = renderer_->HasVideo(); | |
707 metadata.timeline_offset = demuxer_->GetTimelineOffset(); | 705 metadata.timeline_offset = demuxer_->GetTimelineOffset(); |
708 DemuxerStream* stream = demuxer_->GetStream(DemuxerStream::VIDEO); | 706 DemuxerStream* stream = demuxer_->GetStream(DemuxerStream::VIDEO); |
709 if (stream) { | 707 if (stream) { |
708 metadata.has_video = true; | |
710 metadata.natural_size = stream->video_decoder_config().natural_size(); | 709 metadata.natural_size = stream->video_decoder_config().natural_size(); |
711 metadata.video_rotation = stream->video_rotation(); | 710 metadata.video_rotation = stream->video_rotation(); |
712 } | 711 } |
713 metadata_cb_.Run(metadata); | 712 if (demuxer_->GetStream(DemuxerStream::AUDIO)) { |
713 metadata.has_audio = true; | |
714 } | |
715 base::ResetAndReturn(&metadata_cb_).Run(metadata); | |
714 } | 716 } |
715 | 717 |
716 void Pipeline::BufferingStateChanged(BufferingState new_buffering_state) { | 718 void Pipeline::BufferingStateChanged(BufferingState new_buffering_state) { |
717 DVLOG(1) << __FUNCTION__ << "(" << new_buffering_state << ") "; | 719 DVLOG(1) << __FUNCTION__ << "(" << new_buffering_state << ") "; |
718 DCHECK(task_runner_->BelongsToCurrentThread()); | 720 DCHECK(task_runner_->BelongsToCurrentThread()); |
719 buffering_state_cb_.Run(new_buffering_state); | 721 buffering_state_cb_.Run(new_buffering_state); |
720 } | 722 } |
721 | 723 |
722 } // namespace media | 724 } // namespace media |
OLD | NEW |