| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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/renderers/renderer_impl.h" | 5 #include "media/renderers/renderer_impl.h" |
| 6 | 6 |
| 7 #include <utility> | 7 #include <utility> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/callback.h" | 10 #include "base/callback.h" |
| (...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 177 pending_cdm_attached_cb_ = cdm_attached_cb; | 177 pending_cdm_attached_cb_ = cdm_attached_cb; |
| 178 | 178 |
| 179 InitializeAudioRenderer(); | 179 InitializeAudioRenderer(); |
| 180 } | 180 } |
| 181 | 181 |
| 182 void RendererImpl::Flush(const base::Closure& flush_cb) { | 182 void RendererImpl::Flush(const base::Closure& flush_cb) { |
| 183 DVLOG(1) << __func__; | 183 DVLOG(1) << __func__; |
| 184 DCHECK(task_runner_->BelongsToCurrentThread()); | 184 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 185 DCHECK(flush_cb_.is_null()); | 185 DCHECK(flush_cb_.is_null()); |
| 186 | 186 |
| 187 if (state_ == STATE_FLUSHED) { |
| 188 task_runner_->PostTask(FROM_HERE, flush_cb); |
| 189 return; |
| 190 } |
| 191 |
| 187 if (state_ != STATE_PLAYING) { | 192 if (state_ != STATE_PLAYING) { |
| 188 DCHECK_EQ(state_, STATE_ERROR); | 193 DCHECK_EQ(state_, STATE_ERROR); |
| 189 return; | 194 return; |
| 190 } | 195 } |
| 191 | 196 |
| 192 flush_cb_ = flush_cb; | 197 flush_cb_ = flush_cb; |
| 193 state_ = STATE_FLUSHING; | 198 state_ = STATE_FLUSHING; |
| 194 | 199 |
| 195 if (time_ticking_) | 200 if (time_ticking_) |
| 196 PausePlayback(); | 201 PausePlayback(); |
| 197 | 202 |
| 198 FlushAudioRenderer(); | 203 FlushAudioRenderer(); |
| 199 } | 204 } |
| 200 | 205 |
| 201 void RendererImpl::StartPlayingFrom(base::TimeDelta time) { | 206 void RendererImpl::StartPlayingFrom(base::TimeDelta time) { |
| 202 DVLOG(1) << __func__; | 207 DVLOG(1) << __func__; |
| 203 DCHECK(task_runner_->BelongsToCurrentThread()); | 208 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 204 | 209 |
| 205 if (state_ != STATE_PLAYING) { | 210 if (state_ != STATE_FLUSHED) { |
| 206 DCHECK_EQ(state_, STATE_ERROR); | 211 DCHECK_EQ(state_, STATE_ERROR); |
| 207 return; | 212 return; |
| 208 } | 213 } |
| 209 | 214 |
| 210 time_source_->SetMediaTime(time); | 215 time_source_->SetMediaTime(time); |
| 211 | 216 |
| 217 state_ = STATE_PLAYING; |
| 212 if (audio_renderer_) | 218 if (audio_renderer_) |
| 213 audio_renderer_->StartPlaying(); | 219 audio_renderer_->StartPlaying(); |
| 214 if (video_renderer_) | 220 if (video_renderer_) |
| 215 video_renderer_->StartPlayingFrom(time); | 221 video_renderer_->StartPlayingFrom(time); |
| 216 } | 222 } |
| 217 | 223 |
| 218 void RendererImpl::OnStreamStatusChanged(DemuxerStream* stream, | 224 void RendererImpl::OnStreamStatusChanged(DemuxerStream* stream, |
| 219 bool enabled, | 225 bool enabled, |
| 220 base::TimeDelta time) { | 226 base::TimeDelta time) { |
| 221 DCHECK(task_runner_->BelongsToCurrentThread()); | 227 DCHECK(task_runner_->BelongsToCurrentThread()); |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 271 DCHECK(audio_renderer_); | 277 DCHECK(audio_renderer_); |
| 272 audio_ended_ = false; | 278 audio_ended_ = false; |
| 273 audio_renderer_->StartPlaying(); | 279 audio_renderer_->StartPlaying(); |
| 274 } | 280 } |
| 275 | 281 |
| 276 void RendererImpl::SetPlaybackRate(double playback_rate) { | 282 void RendererImpl::SetPlaybackRate(double playback_rate) { |
| 277 DVLOG(1) << __func__ << "(" << playback_rate << ")"; | 283 DVLOG(1) << __func__ << "(" << playback_rate << ")"; |
| 278 DCHECK(task_runner_->BelongsToCurrentThread()); | 284 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 279 | 285 |
| 280 // Playback rate changes are only carried out while playing. | 286 // Playback rate changes are only carried out while playing. |
| 281 if (state_ != STATE_PLAYING) | 287 if (state_ != STATE_PLAYING && state_ != STATE_FLUSHED) |
| 282 return; | 288 return; |
| 283 | 289 |
| 284 time_source_->SetPlaybackRate(playback_rate); | 290 time_source_->SetPlaybackRate(playback_rate); |
| 285 | 291 |
| 286 const double old_rate = playback_rate_; | 292 const double old_rate = playback_rate_; |
| 287 playback_rate_ = playback_rate; | 293 playback_rate_ = playback_rate; |
| 288 if (!time_ticking_ || !video_renderer_) | 294 if (!time_ticking_ || !video_renderer_) |
| 289 return; | 295 return; |
| 290 | 296 |
| 291 if (old_rate == 0 && playback_rate > 0) | 297 if (old_rate == 0 && playback_rate > 0) |
| (...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 473 media_resource_->SetStreamStatusChangeCB( | 479 media_resource_->SetStreamStatusChangeCB( |
| 474 base::Bind(&RendererImpl::OnStreamStatusChanged, weak_this_)); | 480 base::Bind(&RendererImpl::OnStreamStatusChanged, weak_this_)); |
| 475 | 481 |
| 476 if (audio_renderer_) { | 482 if (audio_renderer_) { |
| 477 time_source_ = audio_renderer_->GetTimeSource(); | 483 time_source_ = audio_renderer_->GetTimeSource(); |
| 478 } else if (!time_source_) { | 484 } else if (!time_source_) { |
| 479 wall_clock_time_source_.reset(new WallClockTimeSource()); | 485 wall_clock_time_source_.reset(new WallClockTimeSource()); |
| 480 time_source_ = wall_clock_time_source_.get(); | 486 time_source_ = wall_clock_time_source_.get(); |
| 481 } | 487 } |
| 482 | 488 |
| 483 state_ = STATE_PLAYING; | 489 state_ = STATE_FLUSHED; |
| 484 DCHECK(time_source_); | 490 DCHECK(time_source_); |
| 485 DCHECK(audio_renderer_ || video_renderer_); | 491 DCHECK(audio_renderer_ || video_renderer_); |
| 486 | 492 |
| 487 FinishInitialization(PIPELINE_OK); | 493 FinishInitialization(PIPELINE_OK); |
| 488 } | 494 } |
| 489 | 495 |
| 490 void RendererImpl::FlushAudioRenderer() { | 496 void RendererImpl::FlushAudioRenderer() { |
| 491 DVLOG(1) << __func__; | 497 DVLOG(1) << __func__; |
| 492 DCHECK(task_runner_->BelongsToCurrentThread()); | 498 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 493 DCHECK_EQ(state_, STATE_FLUSHING); | 499 DCHECK_EQ(state_, STATE_FLUSHING); |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 545 if (state_ == STATE_ERROR) { | 551 if (state_ == STATE_ERROR) { |
| 546 DCHECK(flush_cb_.is_null()); | 552 DCHECK(flush_cb_.is_null()); |
| 547 return; | 553 return; |
| 548 } | 554 } |
| 549 | 555 |
| 550 DCHECK_EQ(state_, STATE_FLUSHING); | 556 DCHECK_EQ(state_, STATE_FLUSHING); |
| 551 DCHECK(!flush_cb_.is_null()); | 557 DCHECK(!flush_cb_.is_null()); |
| 552 | 558 |
| 553 DCHECK_EQ(video_buffering_state_, BUFFERING_HAVE_NOTHING); | 559 DCHECK_EQ(video_buffering_state_, BUFFERING_HAVE_NOTHING); |
| 554 video_ended_ = false; | 560 video_ended_ = false; |
| 555 state_ = STATE_PLAYING; | 561 state_ = STATE_FLUSHED; |
| 556 base::ResetAndReturn(&flush_cb_).Run(); | 562 base::ResetAndReturn(&flush_cb_).Run(); |
| 557 } | 563 } |
| 558 | 564 |
| 559 void RendererImpl::OnStatisticsUpdate(const PipelineStatistics& stats) { | 565 void RendererImpl::OnStatisticsUpdate(const PipelineStatistics& stats) { |
| 560 DCHECK(task_runner_->BelongsToCurrentThread()); | 566 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 561 client_->OnStatisticsUpdate(stats); | 567 client_->OnStatisticsUpdate(stats); |
| 562 } | 568 } |
| 563 | 569 |
| 564 bool RendererImpl::HandleRestartedStreamBufferingChanges( | 570 bool RendererImpl::HandleRestartedStreamBufferingChanges( |
| 565 DemuxerStream::Type type, | 571 DemuxerStream::Type type, |
| (...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 726 DCHECK(task_runner_->BelongsToCurrentThread()); | 732 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 727 switch (state_) { | 733 switch (state_) { |
| 728 case STATE_PLAYING: | 734 case STATE_PLAYING: |
| 729 DCHECK(PlaybackHasEnded() || WaitingForEnoughData() || restarting_audio_) | 735 DCHECK(PlaybackHasEnded() || WaitingForEnoughData() || restarting_audio_) |
| 730 << "Playback should only pause due to ending or underflowing or" | 736 << "Playback should only pause due to ending or underflowing or" |
| 731 " when restarting audio stream"; | 737 " when restarting audio stream"; |
| 732 | 738 |
| 733 break; | 739 break; |
| 734 | 740 |
| 735 case STATE_FLUSHING: | 741 case STATE_FLUSHING: |
| 742 case STATE_FLUSHED: |
| 736 // It's OK to pause playback when flushing. | 743 // It's OK to pause playback when flushing. |
| 737 break; | 744 break; |
| 738 | 745 |
| 739 case STATE_UNINITIALIZED: | 746 case STATE_UNINITIALIZED: |
| 740 case STATE_INIT_PENDING_CDM: | 747 case STATE_INIT_PENDING_CDM: |
| 741 case STATE_INITIALIZING: | 748 case STATE_INITIALIZING: |
| 742 NOTREACHED() << "Invalid state: " << state_; | 749 NOTREACHED() << "Invalid state: " << state_; |
| 743 break; | 750 break; |
| 744 | 751 |
| 745 case STATE_ERROR: | 752 case STATE_ERROR: |
| (...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 849 DCHECK(task_runner_->BelongsToCurrentThread()); | 856 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 850 client_->OnVideoNaturalSizeChange(size); | 857 client_->OnVideoNaturalSizeChange(size); |
| 851 } | 858 } |
| 852 | 859 |
| 853 void RendererImpl::OnVideoOpacityChange(bool opaque) { | 860 void RendererImpl::OnVideoOpacityChange(bool opaque) { |
| 854 DCHECK(task_runner_->BelongsToCurrentThread()); | 861 DCHECK(task_runner_->BelongsToCurrentThread()); |
| 855 client_->OnVideoOpacityChange(opaque); | 862 client_->OnVideoOpacityChange(opaque); |
| 856 } | 863 } |
| 857 | 864 |
| 858 } // namespace media | 865 } // namespace media |
| OLD | NEW |