OLD | NEW |
1 /* | 1 /* |
2 * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
53 pcm_format_ = CreatePCMConfiguration(audio_parameters_.channels(), | 53 pcm_format_ = CreatePCMConfiguration(audio_parameters_.channels(), |
54 audio_parameters_.sample_rate(), | 54 audio_parameters_.sample_rate(), |
55 audio_parameters_.bits_per_sample()); | 55 audio_parameters_.bits_per_sample()); |
56 // Detach from this thread since we want to use the checker to verify calls | 56 // Detach from this thread since we want to use the checker to verify calls |
57 // from the internal audio thread. | 57 // from the internal audio thread. |
58 thread_checker_opensles_.DetachFromThread(); | 58 thread_checker_opensles_.DetachFromThread(); |
59 } | 59 } |
60 | 60 |
61 OpenSLESPlayer::~OpenSLESPlayer() { | 61 OpenSLESPlayer::~OpenSLESPlayer() { |
62 ALOGD("dtor%s", GetThreadInfo().c_str()); | 62 ALOGD("dtor%s", GetThreadInfo().c_str()); |
63 DCHECK(thread_checker_.CalledOnValidThread()); | 63 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
64 Terminate(); | 64 Terminate(); |
65 DestroyAudioPlayer(); | 65 DestroyAudioPlayer(); |
66 DestroyMix(); | 66 DestroyMix(); |
67 DestroyEngine(); | 67 DestroyEngine(); |
68 DCHECK(!engine_object_.Get()); | 68 RTC_DCHECK(!engine_object_.Get()); |
69 DCHECK(!engine_); | 69 RTC_DCHECK(!engine_); |
70 DCHECK(!output_mix_.Get()); | 70 RTC_DCHECK(!output_mix_.Get()); |
71 DCHECK(!player_); | 71 RTC_DCHECK(!player_); |
72 DCHECK(!simple_buffer_queue_); | 72 RTC_DCHECK(!simple_buffer_queue_); |
73 DCHECK(!volume_); | 73 RTC_DCHECK(!volume_); |
74 } | 74 } |
75 | 75 |
76 int OpenSLESPlayer::Init() { | 76 int OpenSLESPlayer::Init() { |
77 ALOGD("Init%s", GetThreadInfo().c_str()); | 77 ALOGD("Init%s", GetThreadInfo().c_str()); |
78 DCHECK(thread_checker_.CalledOnValidThread()); | 78 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
79 return 0; | 79 return 0; |
80 } | 80 } |
81 | 81 |
82 int OpenSLESPlayer::Terminate() { | 82 int OpenSLESPlayer::Terminate() { |
83 ALOGD("Terminate%s", GetThreadInfo().c_str()); | 83 ALOGD("Terminate%s", GetThreadInfo().c_str()); |
84 DCHECK(thread_checker_.CalledOnValidThread()); | 84 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
85 StopPlayout(); | 85 StopPlayout(); |
86 return 0; | 86 return 0; |
87 } | 87 } |
88 | 88 |
89 int OpenSLESPlayer::InitPlayout() { | 89 int OpenSLESPlayer::InitPlayout() { |
90 ALOGD("InitPlayout%s", GetThreadInfo().c_str()); | 90 ALOGD("InitPlayout%s", GetThreadInfo().c_str()); |
91 DCHECK(thread_checker_.CalledOnValidThread()); | 91 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
92 DCHECK(!initialized_); | 92 RTC_DCHECK(!initialized_); |
93 DCHECK(!playing_); | 93 RTC_DCHECK(!playing_); |
94 CreateEngine(); | 94 CreateEngine(); |
95 CreateMix(); | 95 CreateMix(); |
96 initialized_ = true; | 96 initialized_ = true; |
97 buffer_index_ = 0; | 97 buffer_index_ = 0; |
98 return 0; | 98 return 0; |
99 } | 99 } |
100 | 100 |
101 int OpenSLESPlayer::StartPlayout() { | 101 int OpenSLESPlayer::StartPlayout() { |
102 ALOGD("StartPlayout%s", GetThreadInfo().c_str()); | 102 ALOGD("StartPlayout%s", GetThreadInfo().c_str()); |
103 DCHECK(thread_checker_.CalledOnValidThread()); | 103 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
104 DCHECK(initialized_); | 104 RTC_DCHECK(initialized_); |
105 DCHECK(!playing_); | 105 RTC_DCHECK(!playing_); |
106 // The number of lower latency audio players is limited, hence we create the | 106 // The number of lower latency audio players is limited, hence we create the |
107 // audio player in Start() and destroy it in Stop(). | 107 // audio player in Start() and destroy it in Stop(). |
108 CreateAudioPlayer(); | 108 CreateAudioPlayer(); |
109 // Fill up audio buffers to avoid initial glitch and to ensure that playback | 109 // Fill up audio buffers to avoid initial glitch and to ensure that playback |
110 // starts when mode is later changed to SL_PLAYSTATE_PLAYING. | 110 // starts when mode is later changed to SL_PLAYSTATE_PLAYING. |
111 // TODO(henrika): we can save some delay by only making one call to | 111 // TODO(henrika): we can save some delay by only making one call to |
112 // EnqueuePlayoutData. Most likely not worth the risk of adding a glitch. | 112 // EnqueuePlayoutData. Most likely not worth the risk of adding a glitch. |
113 for (int i = 0; i < kNumOfOpenSLESBuffers; ++i) { | 113 for (int i = 0; i < kNumOfOpenSLESBuffers; ++i) { |
114 EnqueuePlayoutData(); | 114 EnqueuePlayoutData(); |
115 } | 115 } |
116 // Start streaming data by setting the play state to SL_PLAYSTATE_PLAYING. | 116 // Start streaming data by setting the play state to SL_PLAYSTATE_PLAYING. |
117 // For a player object, when the object is in the SL_PLAYSTATE_PLAYING | 117 // For a player object, when the object is in the SL_PLAYSTATE_PLAYING |
118 // state, adding buffers will implicitly start playback. | 118 // state, adding buffers will implicitly start playback. |
119 RETURN_ON_ERROR((*player_)->SetPlayState(player_, SL_PLAYSTATE_PLAYING), -1); | 119 RETURN_ON_ERROR((*player_)->SetPlayState(player_, SL_PLAYSTATE_PLAYING), -1); |
120 playing_ = (GetPlayState() == SL_PLAYSTATE_PLAYING); | 120 playing_ = (GetPlayState() == SL_PLAYSTATE_PLAYING); |
121 DCHECK(playing_); | 121 RTC_DCHECK(playing_); |
122 return 0; | 122 return 0; |
123 } | 123 } |
124 | 124 |
125 int OpenSLESPlayer::StopPlayout() { | 125 int OpenSLESPlayer::StopPlayout() { |
126 ALOGD("StopPlayout%s", GetThreadInfo().c_str()); | 126 ALOGD("StopPlayout%s", GetThreadInfo().c_str()); |
127 DCHECK(thread_checker_.CalledOnValidThread()); | 127 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
128 if (!initialized_ || !playing_) { | 128 if (!initialized_ || !playing_) { |
129 return 0; | 129 return 0; |
130 } | 130 } |
131 // Stop playing by setting the play state to SL_PLAYSTATE_STOPPED. | 131 // Stop playing by setting the play state to SL_PLAYSTATE_STOPPED. |
132 RETURN_ON_ERROR((*player_)->SetPlayState(player_, SL_PLAYSTATE_STOPPED), -1); | 132 RETURN_ON_ERROR((*player_)->SetPlayState(player_, SL_PLAYSTATE_STOPPED), -1); |
133 // Clear the buffer queue to flush out any remaining data. | 133 // Clear the buffer queue to flush out any remaining data. |
134 RETURN_ON_ERROR((*simple_buffer_queue_)->Clear(simple_buffer_queue_), -1); | 134 RETURN_ON_ERROR((*simple_buffer_queue_)->Clear(simple_buffer_queue_), -1); |
135 #ifndef NDEBUG | 135 #ifndef NDEBUG |
136 // Verify that the buffer queue is in fact cleared as it should. | 136 // Verify that the buffer queue is in fact cleared as it should. |
137 SLAndroidSimpleBufferQueueState buffer_queue_state; | 137 SLAndroidSimpleBufferQueueState buffer_queue_state; |
138 (*simple_buffer_queue_)->GetState(simple_buffer_queue_, &buffer_queue_state); | 138 (*simple_buffer_queue_)->GetState(simple_buffer_queue_, &buffer_queue_state); |
139 DCHECK_EQ(0u, buffer_queue_state.count); | 139 RTC_DCHECK_EQ(0u, buffer_queue_state.count); |
140 DCHECK_EQ(0u, buffer_queue_state.index); | 140 RTC_DCHECK_EQ(0u, buffer_queue_state.index); |
141 #endif | 141 #endif |
142 // The number of lower latency audio players is limited, hence we create the | 142 // The number of lower latency audio players is limited, hence we create the |
143 // audio player in Start() and destroy it in Stop(). | 143 // audio player in Start() and destroy it in Stop(). |
144 DestroyAudioPlayer(); | 144 DestroyAudioPlayer(); |
145 thread_checker_opensles_.DetachFromThread(); | 145 thread_checker_opensles_.DetachFromThread(); |
146 initialized_ = false; | 146 initialized_ = false; |
147 playing_ = false; | 147 playing_ = false; |
148 return 0; | 148 return 0; |
149 } | 149 } |
150 | 150 |
(...skipping 13 matching lines...) Expand all Loading... |
164 int OpenSLESPlayer::SetSpeakerVolume(uint32_t volume) { | 164 int OpenSLESPlayer::SetSpeakerVolume(uint32_t volume) { |
165 return -1; | 165 return -1; |
166 } | 166 } |
167 | 167 |
168 int OpenSLESPlayer::SpeakerVolume(uint32_t& volume) const { | 168 int OpenSLESPlayer::SpeakerVolume(uint32_t& volume) const { |
169 return -1; | 169 return -1; |
170 } | 170 } |
171 | 171 |
172 void OpenSLESPlayer::AttachAudioBuffer(AudioDeviceBuffer* audioBuffer) { | 172 void OpenSLESPlayer::AttachAudioBuffer(AudioDeviceBuffer* audioBuffer) { |
173 ALOGD("AttachAudioBuffer"); | 173 ALOGD("AttachAudioBuffer"); |
174 DCHECK(thread_checker_.CalledOnValidThread()); | 174 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
175 audio_device_buffer_ = audioBuffer; | 175 audio_device_buffer_ = audioBuffer; |
176 const int sample_rate_hz = audio_parameters_.sample_rate(); | 176 const int sample_rate_hz = audio_parameters_.sample_rate(); |
177 ALOGD("SetPlayoutSampleRate(%d)", sample_rate_hz); | 177 ALOGD("SetPlayoutSampleRate(%d)", sample_rate_hz); |
178 audio_device_buffer_->SetPlayoutSampleRate(sample_rate_hz); | 178 audio_device_buffer_->SetPlayoutSampleRate(sample_rate_hz); |
179 const int channels = audio_parameters_.channels(); | 179 const int channels = audio_parameters_.channels(); |
180 ALOGD("SetPlayoutChannels(%d)", channels); | 180 ALOGD("SetPlayoutChannels(%d)", channels); |
181 audio_device_buffer_->SetPlayoutChannels(channels); | 181 audio_device_buffer_->SetPlayoutChannels(channels); |
182 CHECK(audio_device_buffer_); | 182 RTC_CHECK(audio_device_buffer_); |
183 AllocateDataBuffers(); | 183 AllocateDataBuffers(); |
184 } | 184 } |
185 | 185 |
186 SLDataFormat_PCM OpenSLESPlayer::CreatePCMConfiguration( | 186 SLDataFormat_PCM OpenSLESPlayer::CreatePCMConfiguration( |
187 int channels, | 187 int channels, |
188 int sample_rate, | 188 int sample_rate, |
189 size_t bits_per_sample) { | 189 size_t bits_per_sample) { |
190 ALOGD("CreatePCMConfiguration"); | 190 ALOGD("CreatePCMConfiguration"); |
191 CHECK_EQ(bits_per_sample, SL_PCMSAMPLEFORMAT_FIXED_16); | 191 RTC_CHECK_EQ(bits_per_sample, SL_PCMSAMPLEFORMAT_FIXED_16); |
192 SLDataFormat_PCM format; | 192 SLDataFormat_PCM format; |
193 format.formatType = SL_DATAFORMAT_PCM; | 193 format.formatType = SL_DATAFORMAT_PCM; |
194 format.numChannels = static_cast<SLuint32>(channels); | 194 format.numChannels = static_cast<SLuint32>(channels); |
195 // Note that, the unit of sample rate is actually in milliHertz and not Hertz. | 195 // Note that, the unit of sample rate is actually in milliHertz and not Hertz. |
196 switch (sample_rate) { | 196 switch (sample_rate) { |
197 case 8000: | 197 case 8000: |
198 format.samplesPerSec = SL_SAMPLINGRATE_8; | 198 format.samplesPerSec = SL_SAMPLINGRATE_8; |
199 break; | 199 break; |
200 case 16000: | 200 case 16000: |
201 format.samplesPerSec = SL_SAMPLINGRATE_16; | 201 format.samplesPerSec = SL_SAMPLINGRATE_16; |
202 break; | 202 break; |
203 case 22050: | 203 case 22050: |
204 format.samplesPerSec = SL_SAMPLINGRATE_22_05; | 204 format.samplesPerSec = SL_SAMPLINGRATE_22_05; |
205 break; | 205 break; |
206 case 32000: | 206 case 32000: |
207 format.samplesPerSec = SL_SAMPLINGRATE_32; | 207 format.samplesPerSec = SL_SAMPLINGRATE_32; |
208 break; | 208 break; |
209 case 44100: | 209 case 44100: |
210 format.samplesPerSec = SL_SAMPLINGRATE_44_1; | 210 format.samplesPerSec = SL_SAMPLINGRATE_44_1; |
211 break; | 211 break; |
212 case 48000: | 212 case 48000: |
213 format.samplesPerSec = SL_SAMPLINGRATE_48; | 213 format.samplesPerSec = SL_SAMPLINGRATE_48; |
214 break; | 214 break; |
215 default: | 215 default: |
216 CHECK(false) << "Unsupported sample rate: " << sample_rate; | 216 RTC_CHECK(false) << "Unsupported sample rate: " << sample_rate; |
217 } | 217 } |
218 format.bitsPerSample = SL_PCMSAMPLEFORMAT_FIXED_16; | 218 format.bitsPerSample = SL_PCMSAMPLEFORMAT_FIXED_16; |
219 format.containerSize = SL_PCMSAMPLEFORMAT_FIXED_16; | 219 format.containerSize = SL_PCMSAMPLEFORMAT_FIXED_16; |
220 format.endianness = SL_BYTEORDER_LITTLEENDIAN; | 220 format.endianness = SL_BYTEORDER_LITTLEENDIAN; |
221 if (format.numChannels == 1) | 221 if (format.numChannels == 1) |
222 format.channelMask = SL_SPEAKER_FRONT_CENTER; | 222 format.channelMask = SL_SPEAKER_FRONT_CENTER; |
223 else if (format.numChannels == 2) | 223 else if (format.numChannels == 2) |
224 format.channelMask = SL_SPEAKER_FRONT_LEFT | SL_SPEAKER_FRONT_RIGHT; | 224 format.channelMask = SL_SPEAKER_FRONT_LEFT | SL_SPEAKER_FRONT_RIGHT; |
225 else | 225 else |
226 CHECK(false) << "Unsupported number of channels: " << format.numChannels; | 226 RTC_CHECK(false) << "Unsupported number of channels: " |
| 227 << format.numChannels; |
227 return format; | 228 return format; |
228 } | 229 } |
229 | 230 |
230 void OpenSLESPlayer::AllocateDataBuffers() { | 231 void OpenSLESPlayer::AllocateDataBuffers() { |
231 ALOGD("AllocateDataBuffers"); | 232 ALOGD("AllocateDataBuffers"); |
232 DCHECK(thread_checker_.CalledOnValidThread()); | 233 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
233 DCHECK(!simple_buffer_queue_); | 234 RTC_DCHECK(!simple_buffer_queue_); |
234 CHECK(audio_device_buffer_); | 235 RTC_CHECK(audio_device_buffer_); |
235 bytes_per_buffer_ = audio_parameters_.GetBytesPerBuffer(); | 236 bytes_per_buffer_ = audio_parameters_.GetBytesPerBuffer(); |
236 ALOGD("native buffer size: %" PRIuS, bytes_per_buffer_); | 237 ALOGD("native buffer size: %" PRIuS, bytes_per_buffer_); |
237 // Create a modified audio buffer class which allows us to ask for any number | 238 // Create a modified audio buffer class which allows us to ask for any number |
238 // of samples (and not only multiple of 10ms) to match the native OpenSL ES | 239 // of samples (and not only multiple of 10ms) to match the native OpenSL ES |
239 // buffer size. | 240 // buffer size. |
240 fine_buffer_.reset(new FineAudioBuffer(audio_device_buffer_, | 241 fine_buffer_.reset(new FineAudioBuffer(audio_device_buffer_, |
241 bytes_per_buffer_, | 242 bytes_per_buffer_, |
242 audio_parameters_.sample_rate())); | 243 audio_parameters_.sample_rate())); |
243 // Each buffer must be of this size to avoid unnecessary memcpy while caching | 244 // Each buffer must be of this size to avoid unnecessary memcpy while caching |
244 // data between successive callbacks. | 245 // data between successive callbacks. |
245 const size_t required_buffer_size = | 246 const size_t required_buffer_size = |
246 fine_buffer_->RequiredPlayoutBufferSizeBytes(); | 247 fine_buffer_->RequiredPlayoutBufferSizeBytes(); |
247 ALOGD("required buffer size: %" PRIuS, required_buffer_size); | 248 ALOGD("required buffer size: %" PRIuS, required_buffer_size); |
248 for (int i = 0; i < kNumOfOpenSLESBuffers; ++i) { | 249 for (int i = 0; i < kNumOfOpenSLESBuffers; ++i) { |
249 audio_buffers_[i].reset(new SLint8[required_buffer_size]); | 250 audio_buffers_[i].reset(new SLint8[required_buffer_size]); |
250 } | 251 } |
251 } | 252 } |
252 | 253 |
253 bool OpenSLESPlayer::CreateEngine() { | 254 bool OpenSLESPlayer::CreateEngine() { |
254 ALOGD("CreateEngine"); | 255 ALOGD("CreateEngine"); |
255 DCHECK(thread_checker_.CalledOnValidThread()); | 256 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
256 if (engine_object_.Get()) | 257 if (engine_object_.Get()) |
257 return true; | 258 return true; |
258 DCHECK(!engine_); | 259 RTC_DCHECK(!engine_); |
259 const SLEngineOption option[] = { | 260 const SLEngineOption option[] = { |
260 {SL_ENGINEOPTION_THREADSAFE, static_cast<SLuint32>(SL_BOOLEAN_TRUE)}}; | 261 {SL_ENGINEOPTION_THREADSAFE, static_cast<SLuint32>(SL_BOOLEAN_TRUE)}}; |
261 RETURN_ON_ERROR( | 262 RETURN_ON_ERROR( |
262 slCreateEngine(engine_object_.Receive(), 1, option, 0, NULL, NULL), | 263 slCreateEngine(engine_object_.Receive(), 1, option, 0, NULL, NULL), |
263 false); | 264 false); |
264 RETURN_ON_ERROR( | 265 RETURN_ON_ERROR( |
265 engine_object_->Realize(engine_object_.Get(), SL_BOOLEAN_FALSE), false); | 266 engine_object_->Realize(engine_object_.Get(), SL_BOOLEAN_FALSE), false); |
266 RETURN_ON_ERROR(engine_object_->GetInterface(engine_object_.Get(), | 267 RETURN_ON_ERROR(engine_object_->GetInterface(engine_object_.Get(), |
267 SL_IID_ENGINE, &engine_), | 268 SL_IID_ENGINE, &engine_), |
268 false); | 269 false); |
269 return true; | 270 return true; |
270 } | 271 } |
271 | 272 |
272 void OpenSLESPlayer::DestroyEngine() { | 273 void OpenSLESPlayer::DestroyEngine() { |
273 ALOGD("DestroyEngine"); | 274 ALOGD("DestroyEngine"); |
274 DCHECK(thread_checker_.CalledOnValidThread()); | 275 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
275 if (!engine_object_.Get()) | 276 if (!engine_object_.Get()) |
276 return; | 277 return; |
277 engine_ = nullptr; | 278 engine_ = nullptr; |
278 engine_object_.Reset(); | 279 engine_object_.Reset(); |
279 } | 280 } |
280 | 281 |
281 bool OpenSLESPlayer::CreateMix() { | 282 bool OpenSLESPlayer::CreateMix() { |
282 ALOGD("CreateMix"); | 283 ALOGD("CreateMix"); |
283 DCHECK(thread_checker_.CalledOnValidThread()); | 284 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
284 DCHECK(engine_); | 285 RTC_DCHECK(engine_); |
285 if (output_mix_.Get()) | 286 if (output_mix_.Get()) |
286 return true; | 287 return true; |
287 | 288 |
288 // Create the ouput mix on the engine object. No interfaces will be used. | 289 // Create the ouput mix on the engine object. No interfaces will be used. |
289 RETURN_ON_ERROR((*engine_)->CreateOutputMix(engine_, output_mix_.Receive(), 0, | 290 RETURN_ON_ERROR((*engine_)->CreateOutputMix(engine_, output_mix_.Receive(), 0, |
290 NULL, NULL), | 291 NULL, NULL), |
291 false); | 292 false); |
292 RETURN_ON_ERROR(output_mix_->Realize(output_mix_.Get(), SL_BOOLEAN_FALSE), | 293 RETURN_ON_ERROR(output_mix_->Realize(output_mix_.Get(), SL_BOOLEAN_FALSE), |
293 false); | 294 false); |
294 return true; | 295 return true; |
295 } | 296 } |
296 | 297 |
297 void OpenSLESPlayer::DestroyMix() { | 298 void OpenSLESPlayer::DestroyMix() { |
298 ALOGD("DestroyMix"); | 299 ALOGD("DestroyMix"); |
299 DCHECK(thread_checker_.CalledOnValidThread()); | 300 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
300 if (!output_mix_.Get()) | 301 if (!output_mix_.Get()) |
301 return; | 302 return; |
302 output_mix_.Reset(); | 303 output_mix_.Reset(); |
303 } | 304 } |
304 | 305 |
305 bool OpenSLESPlayer::CreateAudioPlayer() { | 306 bool OpenSLESPlayer::CreateAudioPlayer() { |
306 ALOGD("CreateAudioPlayer"); | 307 ALOGD("CreateAudioPlayer"); |
307 DCHECK(thread_checker_.CalledOnValidThread()); | 308 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
308 DCHECK(engine_object_.Get()); | 309 RTC_DCHECK(engine_object_.Get()); |
309 DCHECK(output_mix_.Get()); | 310 RTC_DCHECK(output_mix_.Get()); |
310 if (player_object_.Get()) | 311 if (player_object_.Get()) |
311 return true; | 312 return true; |
312 DCHECK(!player_); | 313 RTC_DCHECK(!player_); |
313 DCHECK(!simple_buffer_queue_); | 314 RTC_DCHECK(!simple_buffer_queue_); |
314 DCHECK(!volume_); | 315 RTC_DCHECK(!volume_); |
315 | 316 |
316 // source: Android Simple Buffer Queue Data Locator is source. | 317 // source: Android Simple Buffer Queue Data Locator is source. |
317 SLDataLocator_AndroidSimpleBufferQueue simple_buffer_queue = { | 318 SLDataLocator_AndroidSimpleBufferQueue simple_buffer_queue = { |
318 SL_DATALOCATOR_ANDROIDSIMPLEBUFFERQUEUE, | 319 SL_DATALOCATOR_ANDROIDSIMPLEBUFFERQUEUE, |
319 static_cast<SLuint32>(kNumOfOpenSLESBuffers)}; | 320 static_cast<SLuint32>(kNumOfOpenSLESBuffers)}; |
320 SLDataSource audio_source = {&simple_buffer_queue, &pcm_format_}; | 321 SLDataSource audio_source = {&simple_buffer_queue, &pcm_format_}; |
321 | 322 |
322 // sink: OutputMix-based data is sink. | 323 // sink: OutputMix-based data is sink. |
323 SLDataLocator_OutputMix locator_output_mix = {SL_DATALOCATOR_OUTPUTMIX, | 324 SLDataLocator_OutputMix locator_output_mix = {SL_DATALOCATOR_OUTPUTMIX, |
324 output_mix_.Get()}; | 325 output_mix_.Get()}; |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
382 | 383 |
383 // TODO(henrika): might not be required to set volume to max here since it | 384 // TODO(henrika): might not be required to set volume to max here since it |
384 // seems to be default on most devices. Might be required for unit tests. | 385 // seems to be default on most devices. Might be required for unit tests. |
385 // RETURN_ON_ERROR((*volume_)->SetVolumeLevel(volume_, 0), false); | 386 // RETURN_ON_ERROR((*volume_)->SetVolumeLevel(volume_, 0), false); |
386 | 387 |
387 return true; | 388 return true; |
388 } | 389 } |
389 | 390 |
390 void OpenSLESPlayer::DestroyAudioPlayer() { | 391 void OpenSLESPlayer::DestroyAudioPlayer() { |
391 ALOGD("DestroyAudioPlayer"); | 392 ALOGD("DestroyAudioPlayer"); |
392 DCHECK(thread_checker_.CalledOnValidThread()); | 393 RTC_DCHECK(thread_checker_.CalledOnValidThread()); |
393 if (!player_object_.Get()) | 394 if (!player_object_.Get()) |
394 return; | 395 return; |
395 player_object_.Reset(); | 396 player_object_.Reset(); |
396 player_ = nullptr; | 397 player_ = nullptr; |
397 simple_buffer_queue_ = nullptr; | 398 simple_buffer_queue_ = nullptr; |
398 volume_ = nullptr; | 399 volume_ = nullptr; |
399 } | 400 } |
400 | 401 |
401 // static | 402 // static |
402 void OpenSLESPlayer::SimpleBufferQueueCallback( | 403 void OpenSLESPlayer::SimpleBufferQueueCallback( |
403 SLAndroidSimpleBufferQueueItf caller, | 404 SLAndroidSimpleBufferQueueItf caller, |
404 void* context) { | 405 void* context) { |
405 OpenSLESPlayer* stream = reinterpret_cast<OpenSLESPlayer*>(context); | 406 OpenSLESPlayer* stream = reinterpret_cast<OpenSLESPlayer*>(context); |
406 stream->FillBufferQueue(); | 407 stream->FillBufferQueue(); |
407 } | 408 } |
408 | 409 |
409 void OpenSLESPlayer::FillBufferQueue() { | 410 void OpenSLESPlayer::FillBufferQueue() { |
410 DCHECK(thread_checker_opensles_.CalledOnValidThread()); | 411 RTC_DCHECK(thread_checker_opensles_.CalledOnValidThread()); |
411 SLuint32 state = GetPlayState(); | 412 SLuint32 state = GetPlayState(); |
412 if (state != SL_PLAYSTATE_PLAYING) { | 413 if (state != SL_PLAYSTATE_PLAYING) { |
413 ALOGW("Buffer callback in non-playing state!"); | 414 ALOGW("Buffer callback in non-playing state!"); |
414 return; | 415 return; |
415 } | 416 } |
416 EnqueuePlayoutData(); | 417 EnqueuePlayoutData(); |
417 } | 418 } |
418 | 419 |
419 void OpenSLESPlayer::EnqueuePlayoutData() { | 420 void OpenSLESPlayer::EnqueuePlayoutData() { |
420 // Read audio data from the WebRTC source using the FineAudioBuffer object | 421 // Read audio data from the WebRTC source using the FineAudioBuffer object |
421 // to adjust for differences in buffer size between WebRTC (10ms) and native | 422 // to adjust for differences in buffer size between WebRTC (10ms) and native |
422 // OpenSL ES. | 423 // OpenSL ES. |
423 SLint8* audio_ptr = audio_buffers_[buffer_index_].get(); | 424 SLint8* audio_ptr = audio_buffers_[buffer_index_].get(); |
424 fine_buffer_->GetPlayoutData(audio_ptr); | 425 fine_buffer_->GetPlayoutData(audio_ptr); |
425 // Enqueue the decoded audio buffer for playback. | 426 // Enqueue the decoded audio buffer for playback. |
426 SLresult err = | 427 SLresult err = |
427 (*simple_buffer_queue_) | 428 (*simple_buffer_queue_) |
428 ->Enqueue(simple_buffer_queue_, audio_ptr, bytes_per_buffer_); | 429 ->Enqueue(simple_buffer_queue_, audio_ptr, bytes_per_buffer_); |
429 if (SL_RESULT_SUCCESS != err) { | 430 if (SL_RESULT_SUCCESS != err) { |
430 ALOGE("Enqueue failed: %d", err); | 431 ALOGE("Enqueue failed: %d", err); |
431 } | 432 } |
432 buffer_index_ = (buffer_index_ + 1) % kNumOfOpenSLESBuffers; | 433 buffer_index_ = (buffer_index_ + 1) % kNumOfOpenSLESBuffers; |
433 } | 434 } |
434 | 435 |
435 SLuint32 OpenSLESPlayer::GetPlayState() const { | 436 SLuint32 OpenSLESPlayer::GetPlayState() const { |
436 DCHECK(player_); | 437 RTC_DCHECK(player_); |
437 SLuint32 state; | 438 SLuint32 state; |
438 SLresult err = (*player_)->GetPlayState(player_, &state); | 439 SLresult err = (*player_)->GetPlayState(player_, &state); |
439 if (SL_RESULT_SUCCESS != err) { | 440 if (SL_RESULT_SUCCESS != err) { |
440 ALOGE("GetPlayState failed: %d", err); | 441 ALOGE("GetPlayState failed: %d", err); |
441 } | 442 } |
442 return state; | 443 return state; |
443 } | 444 } |
444 | 445 |
445 } // namespace webrtc | 446 } // namespace webrtc |
OLD | NEW |