summaryrefslogtreecommitdiffstats
path: root/media/audio/android
diff options
context:
space:
mode:
authorhenrika@chromium.org <henrika@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-02-20 19:00:04 +0000
committerhenrika@chromium.org <henrika@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-02-20 19:00:04 +0000
commit3989fd396df575f42424e9aa22c3050742a5e486 (patch)
tree3e483eb14689c8aacc95f2aebc74f7eb060c216f /media/audio/android
parente1d51c34fa0d0d9eec1560baa74c4eb726dacdce (diff)
downloadchromium_src-3989fd396df575f42424e9aa22c3050742a5e486.zip
chromium_src-3989fd396df575f42424e9aa22c3050742a5e486.tar.gz
chromium_src-3989fd396df575f42424e9aa22c3050742a5e486.tar.bz2
Volume button now controls media volume for WebAudio.
Today, WebAudio uses the OpenSL ES low-latency audio backend in media/audio but the stream type is always communication mode (which is OK for WebRTC but not for WebAudio). This patch ensures that: - Only switch to system-wide Communication mode when a low-latency input stream is created (e.g. from getUserMedia). - Opens the native output stream in Media mode if system mode is Media and in Communication mode if system mode is Communication. To summarize: an application which renders WebAudio audio should now be able to see the default media volume icon and change the volume accordingly. TEST=http://chromium.googlecode.com/svn/trunk/samples/audio/shiny-drum-machine.html BUG=342114 Review URL: https://codereview.chromium.org/173503003 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@252341 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'media/audio/android')
-rw-r--r--media/audio/android/audio_manager_android.cc40
-rw-r--r--media/audio/android/audio_manager_android.h6
-rw-r--r--media/audio/android/opensles_output.cc11
-rw-r--r--media/audio/android/opensles_output.h7
4 files changed, 36 insertions, 28 deletions
diff --git a/media/audio/android/audio_manager_android.cc b/media/audio/android/audio_manager_android.cc
index a8d81c7..273a741 100644
--- a/media/audio/android/audio_manager_android.cc
+++ b/media/audio/android/audio_manager_android.cc
@@ -45,7 +45,8 @@ AudioManager* CreateAudioManager(AudioLogFactory* audio_log_factory) {
}
AudioManagerAndroid::AudioManagerAndroid(AudioLogFactory* audio_log_factory)
- : AudioManagerBase(audio_log_factory) {
+ : AudioManagerBase(audio_log_factory),
+ communication_mode_is_on_(false) {
SetMaxOutputStreamsAllowed(kMaxOutputStreams);
j_audio_manager_.Reset(
@@ -123,17 +124,8 @@ AudioParameters AudioManagerAndroid::GetInputStreamParameters(
AudioOutputStream* AudioManagerAndroid::MakeAudioOutputStream(
const AudioParameters& params,
const std::string& device_id) {
- bool had_no_streams = HadNoAudioStreams();
AudioOutputStream* stream =
AudioManagerBase::MakeAudioOutputStream(params, std::string());
-
- // The audio manager for Android creates streams intended for real-time
- // VoIP sessions and therefore sets the audio mode to MODE_IN_COMMUNICATION.
- // If a Bluetooth headset is used, the audio stream will use the SCO
- // channel and therefore have a limited bandwidth (8-16kHz).
- if (stream && had_no_streams)
- SetCommunicationAudioModeOn(true);
-
{
base::AutoLock lock(streams_lock_);
streams_.insert(static_cast<OpenSLESOutputStream*>(stream));
@@ -144,7 +136,7 @@ AudioOutputStream* AudioManagerAndroid::MakeAudioOutputStream(
AudioInputStream* AudioManagerAndroid::MakeAudioInputStream(
const AudioParameters& params, const std::string& device_id) {
- bool had_no_streams = HadNoAudioStreams();
+ bool has_no_input_streams = HasNoAudioInputStreams();
AudioInputStream* stream =
AudioManagerBase::MakeAudioInputStream(params, device_id);
@@ -152,18 +144,15 @@ AudioInputStream* AudioManagerAndroid::MakeAudioInputStream(
// VoIP sessions and therefore sets the audio mode to MODE_IN_COMMUNICATION.
// If a Bluetooth headset is used, the audio stream will use the SCO
// channel and therefore have a limited bandwidth (8kHz).
- if (stream && had_no_streams)
+ if (stream && has_no_input_streams) {
+ communication_mode_is_on_ = true;
SetCommunicationAudioModeOn(true);
+ }
return stream;
}
void AudioManagerAndroid::ReleaseOutputStream(AudioOutputStream* stream) {
AudioManagerBase::ReleaseOutputStream(stream);
-
- // Restore the audio mode which was used before the first communication-
- // mode stream was created.
- if (HadNoAudioStreams())
- SetCommunicationAudioModeOn(false);
base::AutoLock lock(streams_lock_);
streams_.erase(static_cast<OpenSLESOutputStream*>(stream));
}
@@ -173,14 +162,16 @@ void AudioManagerAndroid::ReleaseInputStream(AudioInputStream* stream) {
// Restore the audio mode which was used before the first communication-
// mode stream was created.
- if (HadNoAudioStreams())
+ if (HasNoAudioInputStreams()) {
+ communication_mode_is_on_ = false;
SetCommunicationAudioModeOn(false);
+ }
}
AudioOutputStream* AudioManagerAndroid::MakeLinearOutputStream(
const AudioParameters& params) {
DCHECK_EQ(AudioParameters::AUDIO_PCM_LINEAR, params.format());
- return new OpenSLESOutputStream(this, params);
+ return new OpenSLESOutputStream(this, params, SL_ANDROID_STREAM_MEDIA);
}
AudioOutputStream* AudioManagerAndroid::MakeLowLatencyOutputStream(
@@ -188,7 +179,12 @@ AudioOutputStream* AudioManagerAndroid::MakeLowLatencyOutputStream(
const std::string& device_id) {
DLOG_IF(ERROR, !device_id.empty()) << "Not implemented!";
DCHECK_EQ(AudioParameters::AUDIO_PCM_LOW_LATENCY, params.format());
- return new OpenSLESOutputStream(this, params);
+
+ // Set stream type which matches the current system-wide audio mode used by
+ // the Android audio manager.
+ const SLint32 stream_type = communication_mode_is_on_ ?
+ SL_ANDROID_STREAM_VOICE : SL_ANDROID_STREAM_MEDIA;
+ return new OpenSLESOutputStream(this, params, stream_type);
}
AudioInputStream* AudioManagerAndroid::MakeLinearInputStream(
@@ -270,8 +266,8 @@ AudioParameters AudioManagerAndroid::GetPreferredOutputStreamParameters(
sample_rate, bits_per_sample, buffer_size, AudioParameters::NO_EFFECTS);
}
-bool AudioManagerAndroid::HadNoAudioStreams() {
- return output_stream_count() == 0 && input_stream_count() == 0;
+bool AudioManagerAndroid::HasNoAudioInputStreams() {
+ return input_stream_count() == 0;
}
// static
diff --git a/media/audio/android/audio_manager_android.h b/media/audio/android/audio_manager_android.h
index ac67d08..b65e593 100644
--- a/media/audio/android/audio_manager_android.h
+++ b/media/audio/android/audio_manager_android.h
@@ -65,7 +65,7 @@ class MEDIA_EXPORT AudioManagerAndroid : public AudioManagerBase {
const AudioParameters& input_params) OVERRIDE;
private:
- bool HadNoAudioStreams();
+ bool HasNoAudioInputStreams();
void Init();
void Close();
void SetCommunicationAudioModeOn(bool on);
@@ -90,6 +90,10 @@ class MEDIA_EXPORT AudioManagerAndroid : public AudioManagerBase {
// lock is used to guard access to |streams_|.
base::Lock streams_lock_;
+ // Enabled when first input stream is created and set to false when last
+ // input stream is destroyed. Also affects the stream type of output streams.
+ bool communication_mode_is_on_;
+
DISALLOW_COPY_AND_ASSIGN(AudioManagerAndroid);
};
diff --git a/media/audio/android/opensles_output.cc b/media/audio/android/opensles_output.cc
index b71680f..41c03c7 100644
--- a/media/audio/android/opensles_output.cc
+++ b/media/audio/android/opensles_output.cc
@@ -20,8 +20,10 @@
namespace media {
OpenSLESOutputStream::OpenSLESOutputStream(AudioManagerAndroid* manager,
- const AudioParameters& params)
+ const AudioParameters& params,
+ SLint32 stream_type)
: audio_manager_(manager),
+ stream_type_(stream_type),
callback_(NULL),
player_(NULL),
simple_buffer_queue_(NULL),
@@ -30,7 +32,8 @@ OpenSLESOutputStream::OpenSLESOutputStream(AudioManagerAndroid* manager,
started_(false),
muted_(false),
volume_(1.0) {
- DVLOG(2) << "OpenSLESOutputStream::OpenSLESOutputStream()";
+ DVLOG(2) << "OpenSLESOutputStream::OpenSLESOutputStream("
+ << "stream_type=" << stream_type << ")";
format_.formatType = SL_DATAFORMAT_PCM;
format_.numChannels = static_cast<SLuint32>(params.channels());
// Provides sampling rate in milliHertz to OpenSLES.
@@ -248,11 +251,11 @@ bool OpenSLESOutputStream::CreatePlayer() {
player_object_.Get(), SL_IID_ANDROIDCONFIGURATION, &player_config),
false);
- SLint32 stream_type = SL_ANDROID_STREAM_VOICE;
+ // Set configuration using the stream type provided at construction.
LOG_ON_FAILURE_AND_RETURN(
(*player_config)->SetConfiguration(player_config,
SL_ANDROID_KEY_STREAM_TYPE,
- &stream_type,
+ &stream_type_,
sizeof(SLint32)),
false);
diff --git a/media/audio/android/opensles_output.h b/media/audio/android/opensles_output.h
index 623b019..b0b678c 100644
--- a/media/audio/android/opensles_output.h
+++ b/media/audio/android/opensles_output.h
@@ -28,7 +28,8 @@ class OpenSLESOutputStream : public AudioOutputStream {
static const int kMaxNumOfBuffersInQueue = 2;
OpenSLESOutputStream(AudioManagerAndroid* manager,
- const AudioParameters& params);
+ const AudioParameters& params,
+ SLint32 stream_type);
virtual ~OpenSLESOutputStream();
@@ -77,6 +78,10 @@ class OpenSLESOutputStream : public AudioOutputStream {
AudioManagerAndroid* audio_manager_;
+ // Audio playback stream type.
+ // See SLES/OpenSLES_Android.h for details.
+ SLint32 stream_type_;
+
AudioSourceCallback* callback_;
// Shared engine interfaces for the app.