Home | History | Annotate | Download | only in media
      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
      3 // found in the LICENSE file.
      4 
      5 #ifndef CONTENT_RENDERER_MEDIA_WEBRTC_AUDIO_CAPTURER_H_
      6 #define CONTENT_RENDERER_MEDIA_WEBRTC_AUDIO_CAPTURER_H_
      7 
      8 #include <list>
      9 #include <string>
     10 
     11 #include "base/callback.h"
     12 #include "base/memory/ref_counted.h"
     13 #include "base/synchronization/lock.h"
     14 #include "base/threading/thread_checker.h"
     15 #include "base/time/time.h"
     16 #include "content/renderer/media/tagged_list.h"
     17 #include "content/renderer/media/webrtc_audio_device_impl.h"
     18 #include "media/audio/audio_input_device.h"
     19 #include "media/base/audio_capturer_source.h"
     20 
     21 namespace media {
     22 class AudioBus;
     23 }
     24 
     25 namespace content {
     26 
     27 class WebRtcLocalAudioRenderer;
     28 class WebRtcLocalAudioTrack;
     29 
     30 // This class manages the capture data flow by getting data from its
     31 // |source_|, and passing it to its |tracks_|.
     32 // It allows clients to inject their own capture data source by calling
     33 // SetCapturerSource().
     34 // The threading model for this class is rather complex since it will be
     35 // created on the main render thread, captured data is provided on a dedicated
     36 // AudioInputDevice thread, and methods can be called either on the Libjingle
     37 // thread or on the main render thread but also other client threads
     38 // if an alternative AudioCapturerSource has been set.
     39 class CONTENT_EXPORT WebRtcAudioCapturer
     40     : public base::RefCountedThreadSafe<WebRtcAudioCapturer>,
     41       NON_EXPORTED_BASE(public media::AudioCapturerSource::CaptureCallback) {
     42  public:
     43   // Use to construct the audio capturer.
     44   // Called on the main render thread.
     45   static scoped_refptr<WebRtcAudioCapturer> CreateCapturer();
     46 
     47   // Creates and configures the default audio capturing source using the
     48   // provided audio parameters.  |render_view_id| specifies the render view
     49   // consuming audio for capture.  |session_id| is passed to the browser to
     50   // decide which device to use.  |device_id| is used to identify which device
     51   // the capturer is created for.  Called on the main render thread.
     52   bool Initialize(int render_view_id,
     53                   media::ChannelLayout channel_layout,
     54                   int sample_rate,
     55                   int buffer_size,
     56                   int session_id,
     57                   const std::string& device_id,
     58                   int paired_output_sample_rate,
     59                   int paired_output_frames_per_buffer,
     60                   int effects);
     61 
     62   // Add a audio track to the sinks of the capturer.
     63   // WebRtcAudioDeviceImpl calls this method on the main render thread but
     64   // other clients may call it from other threads. The current implementation
     65   // does not support multi-thread calling.
     66   // The first AddTrack will implicitly trigger the Start() of this object.
     67   // Called on the main render thread or libjingle working thread.
     68   void AddTrack(WebRtcLocalAudioTrack* track);
     69 
     70   // Remove a audio track from the sinks of the capturer.
     71   // If the track has been added to the capturer, it  must call RemoveTrack()
     72   // before it goes away.
     73   // Called on the main render thread or libjingle working thread.
     74   void RemoveTrack(WebRtcLocalAudioTrack* track);
     75 
     76   // SetCapturerSource() is called if the client on the source side desires to
     77   // provide their own captured audio data. Client is responsible for calling
     78   // Start() on its own source to have the ball rolling.
     79   // Called on the main render thread.
     80   void SetCapturerSource(
     81       const scoped_refptr<media::AudioCapturerSource>& source,
     82       media::ChannelLayout channel_layout,
     83       float sample_rate,
     84       int effects);
     85 
     86   // Called when a stream is connecting to a peer connection. This will set
     87   // up the native buffer size for the stream in order to optimize the
     88   // performance for peer connection.
     89   void EnablePeerConnectionMode();
     90 
     91   // Volume APIs used by WebRtcAudioDeviceImpl.
     92   // Called on the AudioInputDevice audio thread.
     93   void SetVolume(int volume);
     94   int Volume() const;
     95   int MaxVolume() const;
     96 
     97   bool is_recording() const { return running_; }
     98 
     99   // Audio parameters utilized by the audio capturer. Can be utilized by
    100   // a local renderer to set up a renderer using identical parameters as the
    101   // capturer.
    102   // TODO(phoglund): This accessor is inherently unsafe since the returned
    103   // parameters can become outdated at any time. Think over the implications
    104   // of this accessor and if we can remove it.
    105   media::AudioParameters audio_parameters() const;
    106 
    107   // Gets information about the paired output device. Returns true if such a
    108   // device exists.
    109   bool GetPairedOutputParameters(int* session_id,
    110                                  int* output_sample_rate,
    111                                  int* output_frames_per_buffer) const;
    112 
    113   const std::string& device_id() const { return device_id_; }
    114   int session_id() const { return session_id_; }
    115 
    116   // Stops recording audio. This method will empty its track lists since
    117   // stopping the capturer will implicitly invalidate all its tracks.
    118   // This method is exposed to the public because the media stream track can
    119   // call Stop() on its source.
    120   void Stop();
    121 
    122   // Called by the WebAudioCapturerSource to get the audio processing params.
    123   // This function is triggered by provideInput() on the WebAudio audio thread,
    124   // TODO(xians): Remove after moving APM from WebRtc to Chrome.
    125   void GetAudioProcessingParams(base::TimeDelta* delay, int* volume,
    126                                 bool* key_pressed);
    127 
    128  protected:
    129   friend class base::RefCountedThreadSafe<WebRtcAudioCapturer>;
    130   WebRtcAudioCapturer();
    131   virtual ~WebRtcAudioCapturer();
    132 
    133  private:
    134   class TrackOwner;
    135   typedef TaggedList<TrackOwner> TrackList;
    136 
    137   // AudioCapturerSource::CaptureCallback implementation.
    138   // Called on the AudioInputDevice audio thread.
    139   virtual void Capture(media::AudioBus* audio_source,
    140                        int audio_delay_milliseconds,
    141                        double volume,
    142                        bool key_pressed) OVERRIDE;
    143   virtual void OnCaptureError() OVERRIDE;
    144 
    145   // Reconfigures the capturer with a new capture parameters.
    146   // Must be called without holding the lock.
    147   void Reconfigure(int sample_rate, media::ChannelLayout channel_layout,
    148                    int effects);
    149 
    150   // Starts recording audio.
    151   // Triggered by AddSink() on the main render thread or a Libjingle working
    152   // thread. It should NOT be called under |lock_|.
    153   void Start();
    154 
    155   // Helper function to get the buffer size based on |peer_connection_mode_|
    156   // and sample rate;
    157   int GetBufferSize(int sample_rate) const;
    158 
    159   // Used to DCHECK that we are called on the correct thread.
    160   base::ThreadChecker thread_checker_;
    161 
    162   // Protects |source_|, |audio_tracks_|, |running_|, |loopback_fifo_|,
    163   // |params_| and |buffering_|.
    164   mutable base::Lock lock_;
    165 
    166   // A tagged list of audio tracks that the audio data is fed
    167   // to. Tagged items need to be notified that the audio format has
    168   // changed.
    169   TrackList tracks_;
    170 
    171   // The audio data source from the browser process.
    172   scoped_refptr<media::AudioCapturerSource> source_;
    173 
    174   // Cached audio parameters for output.
    175   media::AudioParameters params_;
    176 
    177   bool running_;
    178 
    179   int render_view_id_;
    180 
    181   // Cached value for the hardware native buffer size, used when
    182   // |peer_connection_mode_| is set to false.
    183   int hardware_buffer_size_;
    184 
    185   // The media session ID used to identify which input device to be started by
    186   // the browser.
    187   int session_id_;
    188 
    189   // The device this capturer is given permission to use.
    190   std::string device_id_;
    191 
    192   // Stores latest microphone volume received in a CaptureData() callback.
    193   // Range is [0, 255].
    194   int volume_;
    195 
    196   // Flag which affects the buffer size used by the capturer.
    197   bool peer_connection_mode_;
    198 
    199   int output_sample_rate_;
    200   int output_frames_per_buffer_;
    201 
    202   // Cache value for the audio processing params.
    203   base::TimeDelta audio_delay_;
    204   bool key_pressed_;
    205 
    206   DISALLOW_COPY_AND_ASSIGN(WebRtcAudioCapturer);
    207 };
    208 
    209 }  // namespace content
    210 
    211 #endif  // CONTENT_RENDERER_MEDIA_WEBRTC_AUDIO_CAPTURER_H_
    212