• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2024 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.settings.development;
18 
19 import android.bluetooth.BluetoothAdapter;
20 import android.bluetooth.BluetoothManager;
21 import android.bluetooth.BluetoothStatusCodes;
22 import android.content.Context;
23 import android.os.SystemProperties;
24 import android.sysprop.BluetoothProperties;
25 import android.text.TextUtils;
26 
27 import androidx.annotation.NonNull;
28 import androidx.annotation.Nullable;
29 import androidx.annotation.VisibleForTesting;
30 import androidx.preference.ListPreference;
31 import androidx.preference.Preference;
32 
33 import com.android.settings.R;
34 import com.android.settings.core.PreferenceControllerMixin;
35 import com.android.settingslib.development.DeveloperOptionsPreferenceController;
36 
37 import java.util.Objects;
38 
39 /** Preference controller to control Bluetooth LE audio mode */
40 public class BluetoothLeAudioModePreferenceController extends DeveloperOptionsPreferenceController
41         implements Preference.OnPreferenceChangeListener, PreferenceControllerMixin {
42 
43     private static final String PREFERENCE_KEY = "bluetooth_leaudio_mode";
44 
45     static final String LE_AUDIO_DYNAMIC_SWITCHER_MODE_PROPERTY =
46             "persist.bluetooth.leaudio_dynamic_switcher.mode";
47 
48     @Nullable private final DevelopmentSettingsDashboardFragment mFragment;
49 
50     private final String[] mListValues;
51     private final String[] mListSummaries;
52     @VisibleForTesting @Nullable String mNewMode;
53     @VisibleForTesting BluetoothAdapter mBluetoothAdapter;
54 
55     boolean mChanged = false;
56 
BluetoothLeAudioModePreferenceController( @onNull Context context, @Nullable DevelopmentSettingsDashboardFragment fragment)57     public BluetoothLeAudioModePreferenceController(
58             @NonNull Context context, @Nullable DevelopmentSettingsDashboardFragment fragment) {
59         super(context);
60         mFragment = fragment;
61         mBluetoothAdapter = context.getSystemService(BluetoothManager.class).getAdapter();
62 
63         mListValues = context.getResources().getStringArray(R.array.bluetooth_leaudio_mode_values);
64         mListSummaries = context.getResources().getStringArray(R.array.bluetooth_leaudio_mode);
65     }
66 
67     @Override
68     @NonNull
getPreferenceKey()69     public String getPreferenceKey() {
70         return PREFERENCE_KEY;
71     }
72 
73     @Override
isAvailable()74     public boolean isAvailable() {
75         return BluetoothProperties.isProfileBapBroadcastSourceEnabled().orElse(false);
76     }
77 
78     @Override
onPreferenceChange(@onNull Preference preference, Object newValue)79     public boolean onPreferenceChange(@NonNull Preference preference, Object newValue) {
80         if (mFragment == null) {
81             return false;
82         }
83 
84         BluetoothRebootDialog.show(mFragment);
85         mChanged = true;
86         mNewMode = newValue.toString();
87         return false;
88     }
89 
90     @Override
updateState(@onNull Preference preference)91     public void updateState(@NonNull Preference preference) {
92         if (mBluetoothAdapter == null) {
93             return;
94         }
95 
96         String currentValue;
97         if (mBluetoothAdapter.isLeAudioBroadcastSourceSupported()
98                 == BluetoothStatusCodes.FEATURE_SUPPORTED) {
99             currentValue = "broadcast";
100         } else if (mBluetoothAdapter.isLeAudioSupported()
101                 == BluetoothStatusCodes.FEATURE_SUPPORTED) {
102             currentValue = "unicast";
103         } else {
104             currentValue = "disabled";
105         }
106 
107         int index = 0;
108         for (int i = 0; i < mListValues.length; i++) {
109             if (TextUtils.equals(currentValue, mListValues[i])) {
110                 index = i;
111                 break;
112             }
113         }
114 
115         final ListPreference listPreference = (ListPreference) preference;
116         listPreference.setValue(mListValues[index]);
117         listPreference.setSummary(mListSummaries[index]);
118 
119         if (!mBluetoothAdapter.isEnabled()) {
120             listPreference.setEnabled(false);
121             return;
122         }
123     }
124 
125     /** Called when the RebootDialog confirm is clicked. */
onRebootDialogConfirmed()126     public void onRebootDialogConfirmed() {
127         if (!mChanged) {
128             return;
129         }
130         SystemProperties.set(LE_AUDIO_DYNAMIC_SWITCHER_MODE_PROPERTY, mNewMode);
131         if (mFragment != null && !Objects.equals(mNewMode, "broadcast")) {
132             mFragment.onBroadcastDisabled();
133         }
134     }
135 
136     /** Called when the RebootDialog cancel is clicked. */
onRebootDialogCanceled()137     public void onRebootDialogCanceled() {
138         mChanged = false;
139     }
140 
141     public interface OnModeChangeListener {
142 
143         /** Called when the broadcast mode is disabled. */
onBroadcastDisabled()144         void onBroadcastDisabled();
145     }
146 }
147