Chromium Code Reviews| Index: content/renderer/media/audio_renderer_impl.cc |
| =================================================================== |
| --- content/renderer/media/audio_renderer_impl.cc (revision 114311) |
| +++ content/renderer/media/audio_renderer_impl.cc (working copy) |
| @@ -38,13 +38,17 @@ |
| AudioRendererImpl::AudioRendererImpl() |
| : AudioRendererBase(), |
| bytes_per_second_(0), |
| - stopped_(false) { |
| + stopped_(false), |
| + is_initialized_(false) { |
| // We create the AudioDevice here because it must be created in the |
| // main thread. But we don't yet know the audio format (sample-rate, etc.) |
| // at this point. Later, when OnInitialize() is called, we have |
| // the audio format information and call the AudioDevice::Initialize() |
| // method to fully initialize it. |
| audio_device_ = new AudioDevice(); |
| + |
| + // Assign the AudioDevice as the default audio sink. |
| + sink_ = audio_device_.get(); |
| } |
| AudioRendererImpl::~AudioRendererImpl() { |
| @@ -90,17 +94,20 @@ |
| bytes_per_second_ = audio_parameters_.GetBytesPerSecond(); |
| - DCHECK(audio_device_.get()); |
| + base::AutoLock auto_lock(sink_lock_); |
| - if (!audio_device_->IsInitialized()) { |
| - audio_device_->Initialize( |
| + DCHECK(sink_); |
| + |
| + if (!is_initialized_) { |
| + sink_->Initialize( |
| GetBufferSizeForSampleRate(sample_rate), |
| audio_parameters_.channels, |
| audio_parameters_.sample_rate, |
| audio_parameters_.format, |
| this); |
| - audio_device_->Start(); |
| + sink_->Start(); |
| + is_initialized_ = true; |
| } |
| return true; |
| @@ -110,8 +117,9 @@ |
| if (stopped_) |
| return; |
| - DCHECK(audio_device_.get()); |
| - audio_device_->Stop(); |
| + base::AutoLock auto_lock(sink_lock_); |
| + DCHECK(sink_); |
| + sink_->Stop(); |
| stopped_ = true; |
| } |
| @@ -169,27 +177,31 @@ |
| void AudioRendererImpl::SetVolume(float volume) { |
| if (stopped_) |
| return; |
| - DCHECK(audio_device_.get()); |
| - audio_device_->SetVolume(volume); |
| + base::AutoLock auto_lock(sink_lock_); |
| + DCHECK(sink_); |
| + sink_->SetVolume(volume); |
| } |
| void AudioRendererImpl::DoPlay() { |
| earliest_end_time_ = base::Time::Now(); |
| - DCHECK(audio_device_.get()); |
| - audio_device_->Play(); |
| + base::AutoLock auto_lock(sink_lock_); |
| + DCHECK(sink_); |
| + sink_->Play(); |
| } |
| void AudioRendererImpl::DoPause() { |
| - DCHECK(audio_device_.get()); |
| - audio_device_->Pause(false); |
| + base::AutoLock auto_lock(sink_lock_); |
| + DCHECK(sink_); |
| + sink_->Pause(false); |
| } |
| void AudioRendererImpl::DoSeek() { |
| earliest_end_time_ = base::Time::Now(); |
| // Pause and flush the stream when we seek to a new location. |
| - DCHECK(audio_device_.get()); |
| - audio_device_->Pause(true); |
| + base::AutoLock auto_lock(sink_lock_); |
| + DCHECK(sink_); |
| + sink_->Pause(true); |
| } |
| void AudioRendererImpl::Render(const std::vector<float*>& audio_data, |
| @@ -245,3 +257,39 @@ |
| } |
| } |
| } |
| + |
| +void AudioRendererImpl::SetAudioRendererSink(media::AudioRendererSink* sink) { |
| + // NULL should be passed in to use the default AudioDevice sink. |
| + DCHECK_NE(sink, audio_device_.get()); |
| + |
| + // Synchronize with other uses of sink_ since we're messing with it here. |
| + base::AutoLock auto_lock(sink_lock_); |
| + |
| + if (sink && sink != sink_) { |
| + // We're switching rendering to a different sink than the AudioDevice. |
| + |
| + // Since we're no longer rendering to the AudioDevice, we don't want |
| + // it to make callbacks to us any more. |
|
tommi (sloooow) - chröme
2011/12/19 15:26:24
nit: anymore
Chris Rogers
2011/12/19 21:40:35
Done.
|
| + if (sink_ == audio_device_.get()) |
| + audio_device_->Pause(true); |
| + |
| + sink_ = sink; |
| + if (is_initialized_) { |
| + // The sink needs to be notified of the audio format, if available. |
| + // If the format is not yet available, it will later be called |
| + // in OnInitialize(). |
| + sink_->Initialize( |
| + GetBufferSizeForSampleRate(audio_parameters_.sample_rate), |
| + audio_parameters_.channels, |
| + audio_parameters_.sample_rate, |
| + audio_parameters_.format, |
| + this); |
| + } |
| + } else if (!sink && sink_ != audio_device_.get()) { |
| + // Use default sink. |
| + sink_ = audio_device_.get(); |
| + |
| + // !!!!! should only call Play() if we're in the playing state. |
|
tommi (sloooow) - chröme
2011/12/19 15:26:24
will you fix this or is it a todo?
do we need to c
Chris Rogers
2011/12/19 21:40:35
Actually, for now I think it's better to do nothin
tommi (sloooow) - chröme
2011/12/20 15:05:46
sounds good.
|
| + audio_device_->Play(); |
| + } |
| +} |