summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothLeBroadcast.java143
-rw-r--r--packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothProfileManager.java2
2 files changed, 98 insertions, 47 deletions
diff --git a/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothLeBroadcast.java b/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothLeBroadcast.java
index 1d2f7902b781..6ee403d50751 100644
--- a/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothLeBroadcast.java
+++ b/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothLeBroadcast.java
@@ -21,6 +21,7 @@ import static android.bluetooth.BluetoothProfile.CONNECTION_POLICY_FORBIDDEN;
import android.annotation.CallbackExecutor;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothClass;
+import android.bluetooth.BluetoothCsipSetCoordinator;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothLeAudioContentMetadata;
import android.bluetooth.BluetoothLeBroadcast;
@@ -62,6 +63,7 @@ import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.Executor;
import java.util.concurrent.Executors;
import java.util.concurrent.ThreadLocalRandom;
+import java.util.stream.Collectors;
/**
* LocalBluetoothLeBroadcast provides an interface between the Settings app and the functionality of
@@ -88,6 +90,8 @@ public class LocalBluetoothLeBroadcast implements LocalBluetoothProfile {
Settings.Secure.BLUETOOTH_LE_BROADCAST_IMPROVE_COMPATIBILITY),
};
+ private final Context mContext;
+ private final CachedBluetoothDeviceManager mDeviceManager;
private BluetoothLeBroadcast mServiceBroadcast;
private BluetoothLeBroadcastAssistant mServiceBroadcastAssistant;
private BluetoothLeAudioContentMetadata mBluetoothLeAudioContentMetadata;
@@ -256,8 +260,19 @@ public class LocalBluetoothLeBroadcast implements LocalBluetoothProfile {
private final BluetoothLeBroadcastAssistant.Callback mBroadcastAssistantCallback =
new BluetoothLeBroadcastAssistant.Callback() {
@Override
- public void onSourceAdded(
- @NonNull BluetoothDevice sink, int sourceId, int reason) {}
+ public void onSourceAdded(@NonNull BluetoothDevice sink, int sourceId, int reason) {
+ if (DEBUG) {
+ Log.d(
+ TAG,
+ "onSourceAdded(), sink = "
+ + sink
+ + ", reason = "
+ + reason
+ + ", sourceId = "
+ + sourceId);
+ }
+ updateFallbackActiveDeviceIfNeeded();
+ }
@Override
public void onSearchStarted(int reason) {}
@@ -301,6 +316,7 @@ public class LocalBluetoothLeBroadcast implements LocalBluetoothProfile {
+ ", sourceId = "
+ sourceId);
}
+ updateFallbackActiveDeviceIfNeeded();
}
@Override
@@ -348,7 +364,9 @@ public class LocalBluetoothLeBroadcast implements LocalBluetoothProfile {
}
}
- LocalBluetoothLeBroadcast(Context context) {
+ LocalBluetoothLeBroadcast(Context context, CachedBluetoothDeviceManager deviceManager) {
+ mContext = context;
+ mDeviceManager = deviceManager;
mExecutor = Executors.newSingleThreadExecutor();
mBuilder = new BluetoothLeAudioContentMetadata.Builder();
mContentResolver = context.getContentResolver();
@@ -430,49 +448,6 @@ public class LocalBluetoothLeBroadcast implements LocalBluetoothProfile {
mServiceBroadcast.startBroadcast(settings);
}
- /**
- * Start the private Broadcast for personal audio sharing or qr code sharing.
- *
- * <p>The broadcast will use random string for both broadcast name and subgroup program info;
- * The broadcast will use random string for broadcast code; The broadcast will only have one
- * subgroup due to system limitation; The subgroup language will be null.
- *
- * <p>If the system started the LE Broadcast, then the system calls the corresponding callback
- * {@link BluetoothLeBroadcast.Callback}.
- */
- public void startPrivateBroadcast(int quality) {
- mNewAppSourceName = "Sharing audio";
- if (mServiceBroadcast == null) {
- Log.d(TAG, "The BluetoothLeBroadcast is null when starting the private broadcast.");
- return;
- }
- if (mServiceBroadcast.getAllBroadcastMetadata().size()
- >= mServiceBroadcast.getMaximumNumberOfBroadcasts()) {
- Log.d(TAG, "Skip starting the broadcast due to number limit.");
- return;
- }
- String programInfo = getProgramInfo();
- if (DEBUG) {
- Log.d(TAG, "startBroadcast: language = null ,programInfo = " + programInfo);
- }
- // Current broadcast framework only support one subgroup
- BluetoothLeBroadcastSubgroupSettings subgroupSettings =
- buildBroadcastSubgroupSettings(
- /* language= */ null,
- programInfo,
- /* improveCompatibility= */
- BluetoothLeBroadcastSubgroupSettings.QUALITY_STANDARD == quality);
- BluetoothLeBroadcastSettings settings =
- buildBroadcastSettings(
- true, // TODO: set to false after framework fix
- TextUtils.isEmpty(programInfo) ? null : programInfo,
- (mBroadcastCode != null && mBroadcastCode.length > 0)
- ? mBroadcastCode
- : null,
- ImmutableList.of(subgroupSettings));
- mServiceBroadcast.startBroadcast(settings);
- }
-
private BluetoothLeBroadcastSettings buildBroadcastSettings(
boolean isPublic,
@Nullable String broadcastName,
@@ -1027,4 +1002,80 @@ public class LocalBluetoothLeBroadcast implements LocalBluetoothProfile {
}
}
}
+
+ /** Update fallback active device if needed. */
+ public void updateFallbackActiveDeviceIfNeeded() {
+ if (!isEnabled(null)) {
+ Log.d(TAG, "Skip updateFallbackActiveDeviceIfNeeded due to no ongoing broadcast");
+ return;
+ }
+ if (mServiceBroadcastAssistant == null) {
+ Log.d(TAG, "Skip updateFallbackActiveDeviceIfNeeded due to assistant profile is null");
+ return;
+ }
+ List<BluetoothDevice> connectedDevices = mServiceBroadcastAssistant.getConnectedDevices();
+ List<BluetoothDevice> devicesInSharing =
+ connectedDevices.stream()
+ .filter(
+ bluetoothDevice -> {
+ List<BluetoothLeBroadcastReceiveState> sourceList =
+ mServiceBroadcastAssistant.getAllSources(
+ bluetoothDevice);
+ return !sourceList.isEmpty();
+ })
+ .collect(Collectors.toList());
+ if (devicesInSharing.isEmpty()) {
+ Log.d(TAG, "Skip updateFallbackActiveDeviceIfNeeded due to no sinks in broadcast");
+ return;
+ }
+ List<BluetoothDevice> devices =
+ BluetoothAdapter.getDefaultAdapter().getMostRecentlyConnectedDevices();
+ BluetoothDevice targetDevice = null;
+ // Find the earliest connected device in sharing session.
+ int targetDeviceIdx = -1;
+ for (BluetoothDevice device : devicesInSharing) {
+ if (devices.contains(device)) {
+ int idx = devices.indexOf(device);
+ if (idx > targetDeviceIdx) {
+ targetDeviceIdx = idx;
+ targetDevice = device;
+ }
+ }
+ }
+ if (targetDevice == null) {
+ Log.d(TAG, "Skip updateFallbackActiveDeviceIfNeeded, target is null");
+ return;
+ }
+ Log.d(
+ TAG,
+ "updateFallbackActiveDeviceIfNeeded, set active device: "
+ + targetDevice.getAnonymizedAddress());
+ CachedBluetoothDevice targetCachedDevice = mDeviceManager.findDevice(targetDevice);
+ if (targetCachedDevice == null) {
+ Log.d(TAG, "Skip updateFallbackActiveDeviceIfNeeded, fail to find cached bt device");
+ return;
+ }
+ int fallbackActiveGroupId = getFallbackActiveGroupId();
+ if (targetCachedDevice.getGroupId() == fallbackActiveGroupId) {
+ Log.d(
+ TAG,
+ "Skip updateFallbackActiveDeviceIfNeeded, already is fallback: "
+ + fallbackActiveGroupId);
+ return;
+ }
+ targetCachedDevice.setActive();
+ }
+
+ private boolean isDecryptedSource(BluetoothLeBroadcastReceiveState state) {
+ return state.getPaSyncState() == BluetoothLeBroadcastReceiveState.PA_SYNC_STATE_SYNCHRONIZED
+ && state.getBigEncryptionState()
+ == BluetoothLeBroadcastReceiveState.BIG_ENCRYPTION_STATE_DECRYPTING;
+ }
+
+ private int getFallbackActiveGroupId() {
+ return Settings.Secure.getInt(
+ mContext.getContentResolver(),
+ "bluetooth_le_broadcast_fallback_active_group_id",
+ BluetoothCsipSetCoordinator.GROUP_ID_INVALID);
+ }
}
diff --git a/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothProfileManager.java b/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothProfileManager.java
index 119aef6da12e..79e4c374667e 100644
--- a/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothProfileManager.java
+++ b/packages/SettingsLib/src/com/android/settingslib/bluetooth/LocalBluetoothProfileManager.java
@@ -257,7 +257,7 @@ public class LocalBluetoothProfileManager {
if (DEBUG) {
Log.d(TAG, "Adding local LE_AUDIO_BROADCAST profile");
}
- mLeAudioBroadcast = new LocalBluetoothLeBroadcast(mContext);
+ mLeAudioBroadcast = new LocalBluetoothLeBroadcast(mContext, mDeviceManager);
// no event handler for the LE boradcast.
mProfileNameMap.put(LocalBluetoothLeBroadcast.NAME, mLeAudioBroadcast);
}