1 /*
2  * Copyright 2018 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.car.settings.bluetooth;
18 
19 import static android.os.UserManager.DISALLOW_BLUETOOTH;
20 
21 import android.bluetooth.BluetoothAdapter;
22 import android.car.drivingstate.CarUxRestrictions;
23 import android.car.userlib.CarUserManagerHelper;
24 import android.content.Context;
25 import android.content.pm.PackageManager;
26 
27 import androidx.annotation.CallSuper;
28 import androidx.preference.Preference;
29 
30 import com.android.car.settings.common.FragmentController;
31 import com.android.car.settings.common.PreferenceController;
32 import com.android.settingslib.bluetooth.BluetoothCallback;
33 import com.android.settingslib.bluetooth.CachedBluetoothDevice;
34 import com.android.settingslib.bluetooth.LocalBluetoothManager;
35 
36 /**
37  * Abstract {@link PreferenceController} that listens to {@link BluetoothCallback} events and
38  * exposes the interface methods for override. It implements a default
39  * {@link #getAvailabilityStatus()} which is {@link #AVAILABLE} when the  system supports
40  * Bluetooth, the current user is not restricted by {@link DISALLOW_BLUETOOTH}, and the default
41  * Bluetooth adapter is enabled.
42  *
43  * @param <V> the upper bound on the type of {@link Preference} on which the controller expects
44  *         to operate.
45  */
46 public abstract class BluetoothPreferenceController<V extends Preference> extends
47         PreferenceController<V> implements BluetoothCallback {
48 
49     private final CarUserManagerHelper mCarUserManagerHelper;
50     private final LocalBluetoothManager mBluetoothManager;
51 
BluetoothPreferenceController(Context context, String preferenceKey, FragmentController fragmentController, CarUxRestrictions uxRestrictions)52     public BluetoothPreferenceController(Context context, String preferenceKey,
53             FragmentController fragmentController, CarUxRestrictions uxRestrictions) {
54         super(context, preferenceKey, fragmentController, uxRestrictions);
55         mCarUserManagerHelper = new CarUserManagerHelper(context);
56         mBluetoothManager = BluetoothUtils.getLocalBtManager(context);
57     }
58 
59     /** Returns a {@link CarUserManagerHelper} constructed from the controller context. */
getCarUserManagerHelper()60     protected final CarUserManagerHelper getCarUserManagerHelper() {
61         return mCarUserManagerHelper;
62     }
63 
64     /**
65      * Returns a {@link LocalBluetoothManager} retrieved with the controller context. This is
66      * not {@code null} unless {@link #getAvailabilityStatus()} returns
67      * {@link #UNSUPPORTED_ON_DEVICE}.
68      */
getBluetoothManager()69     protected final LocalBluetoothManager getBluetoothManager() {
70         return mBluetoothManager;
71     }
72 
73     @Override
getAvailabilityStatus()74     protected int getAvailabilityStatus() {
75         if (!getContext().getPackageManager().hasSystemFeature(PackageManager.FEATURE_BLUETOOTH)) {
76             return UNSUPPORTED_ON_DEVICE;
77         }
78         if (mCarUserManagerHelper.isCurrentProcessUserHasRestriction(DISALLOW_BLUETOOTH)) {
79             return DISABLED_FOR_USER;
80         }
81         return BluetoothAdapter.getDefaultAdapter().isEnabled() ? AVAILABLE
82                 : CONDITIONALLY_UNAVAILABLE;
83     }
84 
85     @Override
86     @CallSuper
onStartInternal()87     protected void onStartInternal() {
88         mBluetoothManager.getEventManager().registerCallback(this);
89     }
90 
91     @Override
92     @CallSuper
onStopInternal()93     protected void onStopInternal() {
94         mBluetoothManager.getEventManager().unregisterCallback(this);
95     }
96 
97     @Override
98     @CallSuper
onBluetoothStateChanged(int bluetoothState)99     public void onBluetoothStateChanged(int bluetoothState) {
100         refreshUi();
101     }
102 
103     @Override
onScanningStateChanged(boolean started)104     public void onScanningStateChanged(boolean started) {
105     }
106 
107     @Override
onDeviceAdded(CachedBluetoothDevice cachedDevice)108     public void onDeviceAdded(CachedBluetoothDevice cachedDevice) {
109     }
110 
111     @Override
onDeviceDeleted(CachedBluetoothDevice cachedDevice)112     public void onDeviceDeleted(CachedBluetoothDevice cachedDevice) {
113     }
114 
115     @Override
onDeviceBondStateChanged(CachedBluetoothDevice cachedDevice, int bondState)116     public void onDeviceBondStateChanged(CachedBluetoothDevice cachedDevice, int bondState) {
117     }
118 
119     @Override
onConnectionStateChanged(CachedBluetoothDevice cachedDevice, int state)120     public void onConnectionStateChanged(CachedBluetoothDevice cachedDevice, int state) {
121     }
122 
123     @Override
onActiveDeviceChanged(CachedBluetoothDevice activeDevice, int bluetoothProfile)124     public void onActiveDeviceChanged(CachedBluetoothDevice activeDevice, int bluetoothProfile) {
125     }
126 
127     @Override
onAudioModeChanged()128     public void onAudioModeChanged() {
129     }
130 }
131