Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(6500)

Unified Diff: chromeos/audio/cras_audio_handler.cc

Issue 14314002: Implement new audio handler which talks to the new audio dbus apis. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: chromeos/audio/cras_audio_handler.cc
diff --git a/chromeos/audio/cras_audio_handler.cc b/chromeos/audio/cras_audio_handler.cc
new file mode 100644
index 0000000000000000000000000000000000000000..30979d07800a51f693cc2b12c5dac3490b9eb144
--- /dev/null
+++ b/chromeos/audio/cras_audio_handler.cc
@@ -0,0 +1,308 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chromeos/audio/cras_audio_handler.h"
+
+#include <algorithm>
+#include <cmath>
+
+#include "base/bind.h"
+#include "base/bind_helpers.h"
+#include "base/logging.h"
+#include "base/prefs/pref_registry_simple.h"
+#include "base/prefs/pref_service.h"
+#include "chromeos/audio/audio_pref_names.h"
+#include "chromeos/dbus/dbus_thread_manager.h"
+
+using std::max;
+using std::min;
+
+namespace chromeos {
+
+namespace {
+
+// Default value for the volume pref, as a percent in the range [0, 100].
+const int kDefaultVolumePercent = 75;
+
+// Default value for unmuting, as a percent in the range [0, 100].
+// Used when sound is unmuted, but volume was less than kMuteThresholdPercent.
+const int kDefaultUnmuteVolumePercent = 4;
+
+// Volume value which should be considered as muted in range [0, 100].
+const int kMuteThresholdPercent = 1;
+
+// Values used for output muted preference.
+const int kPrefOutputMuteOff = 0;
+const int kPrefOutputMuteOn = 1;
+
+static CrasAudioHandler* g_cras_audio_handler = NULL;
+
+} // namespace
+
+CrasAudioHandler::AudioObserver::AudioObserver() {
+}
+
+CrasAudioHandler::AudioObserver::~AudioObserver() {
+}
+
+void CrasAudioHandler::AudioObserver::OnOutputVolumeChanged() {
+}
+
+void CrasAudioHandler::AudioObserver::OnOutputMuteChanged() {
+}
+
+void CrasAudioHandler::AudioObserver::OnInputMuteChanged() {
+}
+
+void CrasAudioHandler::AudioObserver::OnAudioNodesChanged() {
+}
+
+void CrasAudioHandler::AudioObserver::OnActiveOutputNodeChanged() {
+}
+
+void CrasAudioHandler::AudioObserver::OnActiveInputNodeChanged() {
+}
+
+// static
+void CrasAudioHandler::Initialize(PrefService* local_state) {
+ CHECK(!g_cras_audio_handler);
+ g_cras_audio_handler = new CrasAudioHandler(local_state);
+}
+
+// static
+void CrasAudioHandler::Shutdown() {
+ CHECK(g_cras_audio_handler);
+ delete g_cras_audio_handler;
+ g_cras_audio_handler = NULL;
+}
+
+// static
+bool CrasAudioHandler::IsInitialized() {
+ return g_cras_audio_handler != NULL;
+}
+
+// static
+CrasAudioHandler* CrasAudioHandler::Get() {
+ CHECK(g_cras_audio_handler)
+ << "CrasAudioHandler::Get() called before Initialize().";
+ return g_cras_audio_handler;
+}
+
+// static
+void CrasAudioHandler::RegisterPrefs(PrefRegistrySimple* registry) {
+ registry->RegisterDoublePref(prefs::kAudioVolumePercent,
+ kDefaultVolumePercent);
+ registry->RegisterIntegerPref(prefs::kAudioMute, kPrefOutputMuteOff);
+ // Register the prefs backing the audio muting policies.
+ registry->RegisterBooleanPref(prefs::kAudioOutputAllowed, true);
+ // This pref has moved to the media subsystem but we should verify it is there
+ // before we use it.
+ registry->RegisterBooleanPref(prefs::kAudioCaptureAllowed, true);
+}
+
+void CrasAudioHandler::AddAudioObserver(AudioObserver* observer) {
+ observers_.AddObserver(observer);
+}
+
+void CrasAudioHandler::RemoveAudioObserver(AudioObserver* observer) {
+ observers_.RemoveObserver(observer);
+}
+
+bool CrasAudioHandler::IsOutputMuted() {
+ return output_mute_on_;
+}
+
+bool CrasAudioHandler::IsInputMuted() {
+ return input_mute_on_;
+}
+
+int CrasAudioHandler::GetOutputVolumePercent() {
+ return output_volume_;
+}
+
+uint64 CrasAudioHandler::GetActiveOutputNode() const {
+ return active_output_node_id_;
+}
+
+uint64 CrasAudioHandler::GetActiveInputNode() const {
+ return active_input_node_id_;
+}
+
+void CrasAudioHandler::SetOutputVolumePercent(int volume_percent) {
+ volume_percent = min(max(volume_percent, 0), 100);
+ if (volume_percent <= kMuteThresholdPercent)
+ volume_percent = 0;
+ if (IsOutputMuted() && volume_percent > 0)
+ SetOutputMute(false);
+ if (!IsOutputMuted() && volume_percent == 0)
+ SetOutputMute(true);
+ SetOutputVolumeInternal(volume_percent);
+}
+
+void CrasAudioHandler::AdjustOutputVolumeByPercent(int adjust_by_percent) {
+ SetOutputVolumePercent(output_volume_ + adjust_by_percent);
+}
+
+void CrasAudioHandler::SetOutputMute(bool mute_on) {
+ if (output_mute_locked_) {
+ NOTREACHED() << "Output mute has been locked";
+ return;
+ }
+
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->
+ SetOutputMute(mute_on);
+}
+
+void CrasAudioHandler::SetInputMute(bool mute_on) {
+ if (input_mute_locked_) {
+ NOTREACHED() << "Input mute has been locked";
+ return;
+ }
+
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->
+ SetInputMute(mute_on);
+}
+
+void CrasAudioHandler::SetActiveOutputNode(uint64 node_id) {
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->
+ SetActiveOutputNode(node_id);
+}
+
+void CrasAudioHandler::SetActiveInputNode(uint64 node_id) {
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->
+ SetActiveInputNode(node_id);
+}
+
+CrasAudioHandler::CrasAudioHandler(PrefService* local_state)
+ : weak_ptr_factory_(this),
stevenjb 2013/04/17 01:25:12 ALLOW_THIS...
jennyz 2013/04/18 01:21:19 Done.
+ local_state_(local_state),
+ output_mute_on_(false),
+ input_mute_on_(false),
+ output_volume_(0),
+ active_output_node_id_(0),
+ active_input_node_id_(0),
+ output_mute_locked_(false),
+ input_mute_locked_(false) {
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->AddObserver(this);
+ SetupInitialAudioState();
+}
+
+CrasAudioHandler::~CrasAudioHandler() {
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->
+ RemoveObserver(this);
+}
+
+void CrasAudioHandler::AudioClientRestarted() {
+ SetupInitialAudioState();
+}
+
+void CrasAudioHandler::OutputVolumeChanged(int volume) {
+ if (output_volume_ != volume) {
stevenjb 2013/04/17 01:25:12 nit: early exit instead
jennyz 2013/04/18 01:21:19 Done.
+ output_volume_ = volume;
+ local_state_->SetDouble(prefs::kAudioVolumePercent, output_volume_);
+ FOR_EACH_OBSERVER(AudioObserver, observers_, OnOutputVolumeChanged());
+ }
+}
+
+void CrasAudioHandler::OutputMuteChanged(bool mute_on) {
+ if (output_mute_on_ != mute_on) {
stevenjb 2013/04/17 01:25:12 nit: early exit
jennyz 2013/04/18 01:21:19 Done.
+ output_mute_on_ = mute_on;
+ local_state_->SetInteger(
+ prefs::kAudioMute,
+ output_mute_on_ ? kPrefOutputMuteOn : kPrefOutputMuteOff);
+ FOR_EACH_OBSERVER(AudioObserver, observers_, OnOutputMuteChanged());
+ }
+}
+
+void CrasAudioHandler::InputMuteChanged(bool mute_on) {
stevenjb 2013/04/17 01:25:12 nit: early exit
jennyz 2013/04/18 01:21:19 Done.
+ if (input_mute_on_ != mute_on) {
+ input_mute_on_ = mute_on;
+ FOR_EACH_OBSERVER(AudioObserver, observers_, OnInputMuteChanged());
+ }
+}
+
+void CrasAudioHandler::NodesChanged() {
+ // Refresh audio nodes data.
+ GetNodes();
+}
+
+void CrasAudioHandler::ActiveOutputNodeChanged(uint64 node_id) {
+ active_output_node_id_ = node_id;
+ FOR_EACH_OBSERVER(AudioObserver, observers_, OnActiveOutputNodeChanged());
+}
+
+void CrasAudioHandler::ActiveInputNodeChanged(uint64 node_id) {
+ active_input_node_id_ = node_id;
+ FOR_EACH_OBSERVER(AudioObserver, observers_, OnActiveInputNodeChanged());
+}
+
+void CrasAudioHandler::InitializePrefObservers() {
+ pref_change_registrar_.Init(local_state_);
+ base::Closure callback = base::Bind(&CrasAudioHandler::ApplyAudioPolicy,
+ weak_ptr_factory_.GetWeakPtr());
+ pref_change_registrar_.Add(prefs::kAudioOutputAllowed, callback);
+ pref_change_registrar_.Add(prefs::kAudioCaptureAllowed, callback);
+}
+
+void CrasAudioHandler::SetupInitialAudioState() {
+ ApplyAudioPolicy();
+
+ // Set the initial audio state to the ones read from audio prefs.
+ output_mute_on_ =
+ (local_state_->GetInteger(prefs::kAudioMute) == kPrefOutputMuteOn);
+ output_volume_ = local_state_->GetDouble(prefs::kAudioVolumePercent);
+ SetOutputMute(output_mute_on_);
+ SetOutputVolumeInternal(output_volume_);
+
+ // Get the initial audio data.
+ GetNodes();
+}
+
+void CrasAudioHandler::ApplyAudioPolicy() {
+ output_mute_locked_ = false;
+ if (!local_state_->GetBoolean(prefs::kAudioOutputAllowed)) {
+ SetOutputMute(true);
+ output_mute_locked_ = true;
+ }
+
+ input_mute_locked_ = false;
+ if (local_state_->GetBoolean(prefs::kAudioCaptureAllowed)) {
+ SetInputMute(false);
+ } else {
+ SetInputMute(true);
+ input_mute_locked_ = true;
+ }
+}
+
+void CrasAudioHandler::SetOutputVolumeInternal(int volume) {
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->
+ SetOutputVolume(volume);
+}
+
+void CrasAudioHandler::GetNodes() {
+ chromeos::DBusThreadManager::Get()->GetCrasAudioClient()->GetNodes(
+ base::Bind(&CrasAudioHandler::HandleGetNodes,
+ weak_ptr_factory_.GetWeakPtr()));
+}
+
+void CrasAudioHandler::HandleGetNodes(const chromeos::AudioNodeList& node_list,
+ bool success) {
+ if (!success) {
+ LOG(ERROR) << "Failed to retrieve audio nodes data";
+ return;
+ }
+
+ audio_nodes_.clear();
+ for (size_t i = 0; i < node_list.size(); ++i) {
+ if (node_list[i].is_input && node_list[i].active)
+ active_input_node_id_ = node_list[i].id;
+ else if (!node_list[i].is_input && node_list[i].active)
+ active_output_node_id_ = node_list[i].id;
+ audio_nodes_.push_back(node_list[i]);
+ }
+
+ FOR_EACH_OBSERVER(AudioObserver, observers_, OnAudioNodesChanged());
+}
+
+} // namespace chromeos

Powered by Google App Engine
This is Rietveld 408576698