1 /* 2 * libjingle 3 * Copyright 2004 Google Inc. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright notice, 9 * this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright notice, 11 * this list of conditions and the following disclaimer in the documentation 12 * and/or other materials provided with the distribution. 13 * 3. The name of the author may not be used to endorse or promote products 14 * derived from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED 17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 18 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO 19 * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 20 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 21 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 22 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 23 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 24 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 25 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 */ 27 28 #ifndef TALK_SESSION_MEDIA_CHANNELMANAGER_H_ 29 #define TALK_SESSION_MEDIA_CHANNELMANAGER_H_ 30 31 #include <string> 32 #include <vector> 33 34 #include "talk/base/criticalsection.h" 35 #include "talk/base/fileutils.h" 36 #include "talk/base/sigslotrepeater.h" 37 #include "talk/base/thread.h" 38 #include "talk/media/base/capturemanager.h" 39 #include "talk/media/base/mediaengine.h" 40 #include "talk/p2p/base/session.h" 41 #include "talk/session/media/voicechannel.h" 42 43 namespace cricket { 44 45 class Soundclip; 46 class VideoProcessor; 47 class VoiceChannel; 48 class VoiceProcessor; 49 50 // ChannelManager allows the MediaEngine to run on a separate thread, and takes 51 // care of marshalling calls between threads. It also creates and keeps track of 52 // voice and video channels; by doing so, it can temporarily pause all the 53 // channels when a new audio or video device is chosen. The voice and video 54 // channels are stored in separate vectors, to easily allow operations on just 55 // voice or just video channels. 56 // ChannelManager also allows the application to discover what devices it has 57 // using device manager. 58 class ChannelManager : public talk_base::MessageHandler, 59 public sigslot::has_slots<> { 60 public: 61 #if !defined(DISABLE_MEDIA_ENGINE_FACTORY) 62 // Creates the channel manager, and specifies the worker thread to use. 63 explicit ChannelManager(talk_base::Thread* worker); 64 #endif 65 66 // For testing purposes. Allows the media engine and data media 67 // engine and dev manager to be mocks. The ChannelManager takes 68 // ownership of these objects. 69 ChannelManager(MediaEngineInterface* me, 70 DataEngineInterface* dme, 71 DeviceManagerInterface* dm, 72 CaptureManager* cm, 73 talk_base::Thread* worker); 74 // Same as above, but gives an easier default DataEngine. 75 ChannelManager(MediaEngineInterface* me, 76 DeviceManagerInterface* dm, 77 talk_base::Thread* worker); 78 ~ChannelManager(); 79 80 // Accessors for the worker thread, allowing it to be set after construction, 81 // but before Init. set_worker_thread will return false if called after Init. 82 talk_base::Thread* worker_thread() const { return worker_thread_; } 83 bool set_worker_thread(talk_base::Thread* thread) { 84 if (initialized_) return false; 85 worker_thread_ = thread; 86 return true; 87 } 88 89 // Gets capabilities. Can be called prior to starting the media engine. 90 int GetCapabilities(); 91 92 // Retrieves the list of supported audio & video codec types. 93 // Can be called before starting the media engine. 94 void GetSupportedAudioCodecs(std::vector<AudioCodec>* codecs) const; 95 void GetSupportedAudioRtpHeaderExtensions(RtpHeaderExtensions* ext) const; 96 void GetSupportedVideoCodecs(std::vector<VideoCodec>* codecs) const; 97 void GetSupportedVideoRtpHeaderExtensions(RtpHeaderExtensions* ext) const; 98 void GetSupportedDataCodecs(std::vector<DataCodec>* codecs) const; 99 100 // Indicates whether the media engine is started. 101 bool initialized() const { return initialized_; } 102 // Starts up the media engine. 103 bool Init(); 104 // Shuts down the media engine. 105 void Terminate(); 106 107 // The operations below all occur on the worker thread. 108 109 // Creates a voice channel, to be associated with the specified session. 110 VoiceChannel* CreateVoiceChannel( 111 BaseSession* session, const std::string& content_name, bool rtcp); 112 // Destroys a voice channel created with the Create API. 113 void DestroyVoiceChannel(VoiceChannel* voice_channel); 114 // Creates a video channel, synced with the specified voice channel, and 115 // associated with the specified session. 116 VideoChannel* CreateVideoChannel( 117 BaseSession* session, const std::string& content_name, bool rtcp, 118 VoiceChannel* voice_channel); 119 // Destroys a video channel created with the Create API. 120 void DestroyVideoChannel(VideoChannel* video_channel); 121 DataChannel* CreateDataChannel( 122 BaseSession* session, const std::string& content_name, 123 bool rtcp, DataChannelType data_channel_type); 124 // Destroys a data channel created with the Create API. 125 void DestroyDataChannel(DataChannel* data_channel); 126 127 // Creates a soundclip. 128 Soundclip* CreateSoundclip(); 129 // Destroys a soundclip created with the Create API. 130 void DestroySoundclip(Soundclip* soundclip); 131 132 // Indicates whether any channels exist. 133 bool has_channels() const { 134 return (!voice_channels_.empty() || !video_channels_.empty() || 135 !soundclips_.empty()); 136 } 137 138 // Configures the audio and video devices. A null pointer can be passed to 139 // GetAudioOptions() for any parameter of no interest. 140 bool GetAudioOptions(std::string* wave_in_device, 141 std::string* wave_out_device, 142 AudioOptions* options); 143 bool SetAudioOptions(const std::string& wave_in_device, 144 const std::string& wave_out_device, 145 const AudioOptions& options); 146 // Sets Engine-specific audio options according to enabled experiments. 147 bool SetEngineAudioOptions(const AudioOptions& options); 148 bool GetOutputVolume(int* level); 149 bool SetOutputVolume(int level); 150 bool IsSameCapturer(const std::string& capturer_name, 151 VideoCapturer* capturer); 152 // TODO(noahric): Nearly everything called "device" in this API is actually a 153 // device name, so this should really be GetCaptureDeviceName, and the 154 // next method should be GetCaptureDevice. 155 bool GetCaptureDevice(std::string* cam_device); 156 // Gets the current capture Device. 157 bool GetVideoCaptureDevice(Device* device); 158 // Create capturer based on what has been set in SetCaptureDevice(). 159 VideoCapturer* CreateVideoCapturer(); 160 bool SetCaptureDevice(const std::string& cam_device); 161 bool SetDefaultVideoEncoderConfig(const VideoEncoderConfig& config); 162 // RTX will be enabled/disabled in engines that support it. The supporting 163 // engines will start offering an RTX codec. Must be called before Init(). 164 bool SetVideoRtxEnabled(bool enable); 165 166 // Starts/stops the local microphone and enables polling of the input level. 167 bool SetLocalMonitor(bool enable); 168 bool monitoring() const { return monitoring_; } 169 // Sets the local renderer where to renderer the local camera. 170 bool SetLocalRenderer(VideoRenderer* renderer); 171 bool capturing() const { return capturing_; } 172 173 // Configures the logging output of the mediaengine(s). 174 void SetVoiceLogging(int level, const char* filter); 175 void SetVideoLogging(int level, const char* filter); 176 177 // The channel manager handles the Tx side for Video processing, 178 // as well as Tx and Rx side for Voice processing. 179 // (The Rx Video processing will go throug the simplerenderingmanager, 180 // to be implemented). 181 bool RegisterVideoProcessor(VideoCapturer* capturer, 182 VideoProcessor* processor); 183 bool UnregisterVideoProcessor(VideoCapturer* capturer, 184 VideoProcessor* processor); 185 bool RegisterVoiceProcessor(uint32 ssrc, 186 VoiceProcessor* processor, 187 MediaProcessorDirection direction); 188 bool UnregisterVoiceProcessor(uint32 ssrc, 189 VoiceProcessor* processor, 190 MediaProcessorDirection direction); 191 // The following are done in the new "CaptureManager" style that 192 // all local video capturers, processors, and managers should move to. 193 // TODO(pthatcher): Make methods nicer by having start return a handle that 194 // can be used for stop and restart, rather than needing to pass around 195 // formats a a pseudo-handle. 196 bool StartVideoCapture(VideoCapturer* video_capturer, 197 const VideoFormat& video_format); 198 // When muting, produce black frames then pause the camera. 199 // When unmuting, start the camera. Camera starts unmuted. 200 bool MuteToBlackThenPause(VideoCapturer* video_capturer, bool muted); 201 bool StopVideoCapture(VideoCapturer* video_capturer, 202 const VideoFormat& video_format); 203 bool RestartVideoCapture(VideoCapturer* video_capturer, 204 const VideoFormat& previous_format, 205 const VideoFormat& desired_format, 206 CaptureManager::RestartOptions options); 207 208 bool AddVideoRenderer(VideoCapturer* capturer, VideoRenderer* renderer); 209 bool RemoveVideoRenderer(VideoCapturer* capturer, VideoRenderer* renderer); 210 bool IsScreencastRunning() const; 211 212 // The operations below occur on the main thread. 213 214 bool GetAudioInputDevices(std::vector<std::string>* names); 215 bool GetAudioOutputDevices(std::vector<std::string>* names); 216 bool GetVideoCaptureDevices(std::vector<std::string>* names); 217 void SetVideoCaptureDeviceMaxFormat(const std::string& usb_id, 218 const VideoFormat& max_format); 219 220 // Starts AEC dump using existing file. 221 bool StartAecDump(talk_base::PlatformFile file); 222 223 sigslot::repeater0<> SignalDevicesChange; 224 sigslot::signal2<VideoCapturer*, CaptureState> SignalVideoCaptureStateChange; 225 226 // Returns the current selected device. Note: Subtly different from 227 // GetCaptureDevice(). See member video_device_ for more details. 228 // This API is mainly a hook used by unittests. 229 const std::string& video_device_name() const { return video_device_name_; } 230 231 // TODO(hellner): Remove this function once the engine capturer has been 232 // removed. 233 VideoFormat GetStartCaptureFormat(); 234 235 protected: 236 // Adds non-transient parameters which can only be changed through the 237 // options store. 238 bool SetAudioOptions(const std::string& wave_in_device, 239 const std::string& wave_out_device, 240 const AudioOptions& options, 241 int delay_offset); 242 int audio_delay_offset() const { return audio_delay_offset_; } 243 244 private: 245 typedef std::vector<VoiceChannel*> VoiceChannels; 246 typedef std::vector<VideoChannel*> VideoChannels; 247 typedef std::vector<DataChannel*> DataChannels; 248 typedef std::vector<Soundclip*> Soundclips; 249 250 void Construct(MediaEngineInterface* me, 251 DataEngineInterface* dme, 252 DeviceManagerInterface* dm, 253 CaptureManager* cm, 254 talk_base::Thread* worker_thread); 255 void Terminate_w(); 256 VoiceChannel* CreateVoiceChannel_w( 257 BaseSession* session, const std::string& content_name, bool rtcp); 258 void DestroyVoiceChannel_w(VoiceChannel* voice_channel); 259 VideoChannel* CreateVideoChannel_w( 260 BaseSession* session, const std::string& content_name, bool rtcp, 261 VoiceChannel* voice_channel); 262 void DestroyVideoChannel_w(VideoChannel* video_channel); 263 DataChannel* CreateDataChannel_w( 264 BaseSession* session, const std::string& content_name, 265 bool rtcp, DataChannelType data_channel_type); 266 void DestroyDataChannel_w(DataChannel* data_channel); 267 Soundclip* CreateSoundclip_w(); 268 void DestroySoundclip_w(Soundclip* soundclip); 269 bool SetAudioOptions_w(const AudioOptions& options, int delay_offset, 270 const Device* in_dev, const Device* out_dev); 271 bool SetEngineAudioOptions_w(const AudioOptions& options); 272 bool SetCaptureDevice_w(const Device* cam_device); 273 void OnVideoCaptureStateChange(VideoCapturer* capturer, 274 CaptureState result); 275 bool RegisterVideoProcessor_w(VideoCapturer* capturer, 276 VideoProcessor* processor); 277 bool UnregisterVideoProcessor_w(VideoCapturer* capturer, 278 VideoProcessor* processor); 279 bool IsScreencastRunning_w() const; 280 virtual void OnMessage(talk_base::Message *message); 281 282 talk_base::scoped_ptr<MediaEngineInterface> media_engine_; 283 talk_base::scoped_ptr<DataEngineInterface> data_media_engine_; 284 talk_base::scoped_ptr<DeviceManagerInterface> device_manager_; 285 talk_base::scoped_ptr<CaptureManager> capture_manager_; 286 bool initialized_; 287 talk_base::Thread* main_thread_; 288 talk_base::Thread* worker_thread_; 289 290 VoiceChannels voice_channels_; 291 VideoChannels video_channels_; 292 DataChannels data_channels_; 293 Soundclips soundclips_; 294 295 std::string audio_in_device_; 296 std::string audio_out_device_; 297 AudioOptions audio_options_; 298 int audio_delay_offset_; 299 int audio_output_volume_; 300 std::string camera_device_; 301 VideoEncoderConfig default_video_encoder_config_; 302 VideoRenderer* local_renderer_; 303 bool enable_rtx_; 304 305 bool capturing_; 306 bool monitoring_; 307 308 // String containing currently set device. Note that this string is subtly 309 // different from camera_device_. E.g. camera_device_ will list unplugged 310 // but selected devices while this sting will be empty or contain current 311 // selected device. 312 // TODO(hellner): refactor the code such that there is no need to keep two 313 // strings for video devices that have subtle differences in behavior. 314 std::string video_device_name_; 315 }; 316 317 } // namespace cricket 318 319 #endif // TALK_SESSION_MEDIA_CHANNELMANAGER_H_ 320