Chromium Code Reviews| Index: content/renderer/media/media_stream_audio_track.cc |
| diff --git a/content/renderer/media/media_stream_audio_track.cc b/content/renderer/media/media_stream_audio_track.cc |
| index 9eee57d61428d6146bda28f8c930294a8f84857e..efe17b252b702008bb25c5464a5ec1c14ccaa197 100644 |
| --- a/content/renderer/media/media_stream_audio_track.cc |
| +++ b/content/renderer/media/media_stream_audio_track.cc |
| @@ -4,15 +4,17 @@ |
| #include "content/renderer/media/media_stream_audio_track.h" |
| +#include <algorithm> |
| + |
| #include "base/callback_helpers.h" |
| #include "base/logging.h" |
| +#include "content/public/renderer/media_stream_audio_sink.h" |
| #include "third_party/WebKit/public/platform/WebMediaStreamSource.h" |
| -#include "third_party/webrtc/api/mediastreaminterface.h" |
| namespace content { |
| MediaStreamAudioTrack::MediaStreamAudioTrack(bool is_local_track) |
| - : MediaStreamTrack(is_local_track) { |
| + : MediaStreamTrack(is_local_track), is_enabled_(true), weak_factory_(this) { |
| DVLOG(1) << "MediaStreamAudioTrack::MediaStreamAudioTrack(is a " |
| << (is_local_track ? "local" : "remote") << " track)"; |
| } |
| @@ -34,6 +36,56 @@ MediaStreamAudioTrack* MediaStreamAudioTrack::From( |
| return static_cast<MediaStreamAudioTrack*>(track.getExtraData()); |
| } |
| +void MediaStreamAudioTrack::AddSink(MediaStreamAudioSink* sink) { |
| + DCHECK(main_render_thread_checker_.CalledOnValidThread()); |
| + DCHECK(sink); |
| + DVLOG(1) << "MediaStreamAudioTrack::AddSink(" << sink << ')'; |
| + { |
| + base::AutoLock auto_lock(lock_); |
| + DCHECK(std::find(sinks_.begin(), sinks_.end(), sink) == sinks_.end()); |
| + DCHECK(std::find(pending_sinks_.begin(), pending_sinks_.end(), sink) == |
| + pending_sinks_.end()); |
| + pending_sinks_.push_back(sink); |
| + } |
| +} |
| + |
| +void MediaStreamAudioTrack::RemoveSink(MediaStreamAudioSink* sink) { |
| + DCHECK(main_render_thread_checker_.CalledOnValidThread()); |
| + { |
| + base::AutoLock auto_lock(lock_); |
| + auto it = std::find(pending_sinks_.begin(), pending_sinks_.end(), sink); |
| + if (it != pending_sinks_.end()) { |
| + DVLOG(1) << "MediaStreamAudioTrack::RemoveSink(" << sink |
| + << ") from pending sinks list."; |
| + pending_sinks_.erase(it); |
| + } else { |
| + it = std::find(sinks_.begin(), sinks_.end(), sink); |
| + if (it != sinks_.end()) { |
| + DVLOG(1) << "MediaStreamAudioTrack::RemoveSink(" << sink |
| + << ") from active sinks list."; |
| + sinks_.erase(it); |
| + } |
| + } |
| + } |
| +} |
| + |
| +media::AudioParameters MediaStreamAudioTrack::GetOutputFormat() const { |
| + base::AutoLock auto_lock(lock_); |
| + return params_; |
| +} |
| + |
| +void MediaStreamAudioTrack::SetEnabled(bool enabled) { |
| + DCHECK(main_render_thread_checker_.CalledOnValidThread()); |
| + base::AutoLock auto_lock(lock_); |
| + DVLOG(1) << "MediaStreamAudioTrack::SetEnabled(" << (enabled ? 'Y' : 'N') |
| + << "), was previously set to " << (is_enabled_ ? 'Y' : 'N') << '.'; |
| + is_enabled_ = enabled; |
| +} |
| + |
| +void* MediaStreamAudioTrack::GetClassIdentifier() const { |
| + return nullptr; |
| +} |
| + |
| void MediaStreamAudioTrack::Start(const base::Closure& stop_callback) { |
| DCHECK(main_render_thread_checker_.CalledOnValidThread()); |
| DCHECK(!stop_callback.is_null()); |
| @@ -45,16 +97,60 @@ void MediaStreamAudioTrack::Start(const base::Closure& stop_callback) { |
| void MediaStreamAudioTrack::Stop() { |
| DCHECK(main_render_thread_checker_.CalledOnValidThread()); |
| DVLOG(1) << "MediaStreamAudioTrack::Stop()"; |
| + |
| if (!stop_callback_.is_null()) |
| base::ResetAndReturn(&stop_callback_).Run(); |
| + |
| OnStop(); |
| + |
| + std::vector<MediaStreamAudioSink*> sinks_to_notify; |
| + { |
| + base::AutoLock auto_lock(lock_); |
| + sinks_to_notify.swap(sinks_); |
| + sinks_to_notify.insert(sinks_to_notify.end(), pending_sinks_.begin(), |
| + pending_sinks_.end()); |
| + pending_sinks_.clear(); |
| + } |
| + for (MediaStreamAudioSink* sink : sinks_to_notify) |
| + sink->OnReadyStateChanged(blink::WebMediaStreamSource::ReadyStateEnded); |
| + |
| + weak_factory_.InvalidateWeakPtrs(); |
| } |
| void MediaStreamAudioTrack::OnStop() {} |
| -webrtc::AudioTrackInterface* MediaStreamAudioTrack::GetAudioAdapter() { |
| - NOTREACHED(); |
| - return nullptr; |
| +void MediaStreamAudioTrack::SetFormat(const media::AudioParameters& params) { |
| + // Note: May be called on any thread. |
| + base::AutoLock auto_lock(lock_); |
|
o1ka
2016/03/30 15:00:58
According to the header comment, lock_ is not supp
miu
2016/03/31 04:57:59
Fixed header comment.
|
| + if (params_.Equals(params)) |
| + return; |
| + params_ = params; |
| + pending_sinks_.insert(pending_sinks_.end(), sinks_.begin(), sinks_.end()); |
| + sinks_.clear(); |
| +} |
| + |
| +void MediaStreamAudioTrack::DeliverDataToSinks(const media::AudioBus& audio_bus, |
| + base::TimeTicks reference_time) { |
| + // Note: May be called on any thread. |
| + base::AutoLock auto_lock(lock_); |
| + |
| + // If audio delivery is currently disabled, take no actions. |
| + if (!is_enabled_) |
| + return; |
| + |
| + // Call OnSetFormat() for all pending sinks and move them to the |
| + // active-delivery list. |
| + DCHECK(params_.IsValid()); |
| + if (!pending_sinks_.empty()) { |
| + for (MediaStreamAudioSink* sink : pending_sinks_) |
| + sink->OnSetFormat(params_); |
| + sinks_.insert(sinks_.end(), pending_sinks_.begin(), pending_sinks_.end()); |
| + pending_sinks_.clear(); |
| + } |
| + |
| + // Deliver the audio data to each sink. |
| + for (MediaStreamAudioSink* sink : sinks_) |
| + sink->OnData(audio_bus, reference_time); |
| } |
| } // namespace content |