1
    2
    3
    4
    5
    6
    7
    8
    9
   10
   11
   12
   13
   14
   15
   16
   17
   18
   19
   20
   21
   22
   23
   24
   25
   26
   27
   28
   29
   30
   31
   32
   33
   34
   35
   36
   37
   38
   39
   40
   41
   42
   43
   44
   45
   46
   47
   48
   49
   50
   51
   52
   53
   54
   55
   56
   57
   58
   59
   60
   61
   62
   63
   64
   65
   66
   67
   68
   69
   70
   71
   72
   73
   74
   75
   76
   77
   78
   79
   80
   81

ash / system / privacy_hub / speak_on_mute_detection_privacy_switch_controller.cc [blame]

// Copyright 2023 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "ash/system/privacy_hub/speak_on_mute_detection_privacy_switch_controller.h"

#include <memory>

#include "ash/constants/ash_features.h"
#include "ash/constants/ash_pref_names.h"
#include "ash/public/cpp/session/session_observer.h"
#include "ash/session/session_controller_impl.h"
#include "ash/shell.h"
#include "base/check.h"
#include "base/functional/bind.h"
#include "chromeos/ash/components/audio/cras_audio_handler.h"
#include "components/prefs/pref_change_registrar.h"
#include "components/prefs/pref_service.h"

namespace ash {

SpeakOnMuteDetectionPrivacySwitchController::
    SpeakOnMuteDetectionPrivacySwitchController() {
  // Resets the speak-on-mute detection state in CRAS as CRAS is not restarted
  // when chrome restarts.
  CrasAudioHandler::Get()->SetSpeakOnMuteDetection(/*som_on=*/false);

  // Only observes `SessionController` if the feature is enabled.
  if (!features::IsVideoConferenceEnabled()) {
    return;
  }
  SessionControllerImpl* session_controller =
      Shell::Get()->session_controller();
  session_observation_.Observe(session_controller);
}

SpeakOnMuteDetectionPrivacySwitchController::
    ~SpeakOnMuteDetectionPrivacySwitchController() = default;

void SpeakOnMuteDetectionPrivacySwitchController::
    OnActiveUserPrefServiceChanged(PrefService* pref_service) {
  // Subscribes again to pref changes.
  pref_change_registrar_ = std::make_unique<PrefChangeRegistrar>();
  pref_change_registrar_->Init(pref_service);
  pref_change_registrar_->Add(
      prefs::kUserSpeakOnMuteDetectionEnabled,
      base::BindRepeating(&SpeakOnMuteDetectionPrivacySwitchController::
                              SetSpeakOnMuteDetectionFromPref,
                          base::Unretained(this)));
  // Initializes again the speak-on-mute detection local variable.
  speak_on_mute_detection_pref_on_ =
      pref_change_registrar_->prefs()->GetBoolean(
          prefs::kUserSpeakOnMuteDetectionEnabled);

  // Manually sets the speak-on-mute detection state to the value of the user
  // preference when creating the controller during the browser initialization
  // after creating the user profile.
  SetSpeakOnMuteDetectionFromPref();
}

void SpeakOnMuteDetectionPrivacySwitchController::
    SetSpeakOnMuteDetectionFromPref() {
  const bool speak_on_mute_detection_enabled =
      pref_change_registrar_->prefs()->GetBoolean(
          prefs::kUserSpeakOnMuteDetectionEnabled);

  if (speak_on_mute_detection_pref_on_ != speak_on_mute_detection_enabled) {
    speak_on_mute_detection_pref_on_ = speak_on_mute_detection_enabled;
    // No longer shows the opt-in nudge as the speak-on-mute detection pref has
    // changed.
    pref_change_registrar_->prefs()->SetBoolean(
        prefs::kShouldShowSpeakOnMuteOptInNudge, false);
  }

  // Always sends profile state to the CRAS as it can be different from the
  // local state.
  CrasAudioHandler::Get()->SetSpeakOnMuteDetection(
      speak_on_mute_detection_pref_on_);
}

}  // namespace ash