[LeAudio] New QR code scanner UIs and modify local API

Bug: 214340362
Test: manual
Change-Id: I6f654d808dbcb92c99eaad9507b6328a80a0d5f4
Merged-In: I6f654d808dbcb92c99eaad9507b6328a80a0d5f4
This commit is contained in:
Zoey Chen
2022-03-29 17:44:43 +08:00
parent 1a4b945fc4
commit 882f7c4aba
9 changed files with 238 additions and 3 deletions

View File

@@ -0,0 +1,23 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright (C) 2022 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<vector xmlns:android="http://schemas.android.com/apk/res/android" android:width="24dp"
android:height="24dp" android:viewportWidth="24" android:viewportHeight="24"
android:tint="?attr/colorControlNormal">
<path android:fillColor="@android:color/white"
android:pathData="M2,7V2H7V4H4V7ZM2,22V17H4V20H7V22ZM17,22V20H20V17H22V22ZM20,7V4H17V2H22V7ZM17.5,17.5H19V19H17.5ZM17.5,14.5H19V16H17.5ZM16,16H17.5V17.5H16ZM14.5,17.5H16V19H14.5ZM13,16H14.5V17.5H13ZM16,13H17.5V14.5H16ZM14.5,14.5H16V16H14.5ZM13,13H14.5V14.5H13ZM19,5V11H13V5ZM11,13V19H5V13ZM11,5V11H5V5ZM9.5,17.5V14.5H6.5V17.5ZM9.5,9.5V6.5H6.5V9.5ZM17.5,9.5V6.5H14.5V9.5Z"/>
</vector>

View File

@@ -0,0 +1,30 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright (C) 2022 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/root"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<LinearLayout
android:id="@+id/fragment_container"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</LinearLayout>

View File

@@ -0,0 +1,97 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright (C) 2022 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:androidprv="http://schemas.android.com/apk/prv/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="3"
android:layout_marginBottom="35dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:gravity="center"
android:orientation="vertical">
<ImageView
android:src="@drawable/ic_qr_code_scanner"
android:tint="?androidprv:attr/colorAccentPrimaryVariant"
android:layout_width="@dimen/qrcode_icon_size"
android:layout_height="@dimen/qrcode_icon_size"
android:contentDescription="@null"/>
<TextView
style="@style/QrCodeScanner"
android:textSize="24sp"
android:text="@string/bt_le_audio_scan_qr_code"
android:gravity="center"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="19dp"/>
<TextView
style="@style/QrCodeScanner"
android:text="@string/bt_le_audio_scan_qr_code_scanner"
android:gravity="center"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="8dp"/>
</LinearLayout>
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="7"
android:orientation="vertical">
<FrameLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="top"
android:gravity="center"
android:clipChildren="true">
<TextureView
android:id="@+id/preview_view"
android:layout_marginStart="@dimen/qrcode_preview_margin"
android:layout_marginEnd="@dimen/qrcode_preview_margin"
android:layout_width="match_parent"
android:layout_height="@dimen/qrcode_preview_size"/>
</FrameLayout>
<TextView
android:id="@+id/error_message"
style="@style/TextAppearance.ErrorText"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="16dp"
android:layout_marginStart="40dp"
android:layout_marginEnd="40dp"
android:gravity="center"
android:visibility="invisible"/>
</LinearLayout>
</LinearLayout>

View File

@@ -98,4 +98,9 @@
<!-- Minimum width for the popup for updating a user's photo. -->
<dimen name="update_user_photo_popup_min_width">300dp</dimen>
<!-- QR code picture size -->
<dimen name="qrcode_preview_size">360dp</dimen>
<dimen name="qrcode_preview_margin">40dp</dimen>
<dimen name="qrcode_preview_radius">30dp</dimen>
<dimen name="qrcode_icon_size">27dp</dimen>
</resources>

View File

@@ -1531,4 +1531,11 @@
<!-- Content description of the no calling for accessibility (not shown on the screen). [CHAR LIMIT=NONE] -->
<string name="accessibility_no_calling">No calling.</string>
<!-- [CHAR LIMIT=NONE] Le audio QR code scanner title -->
<string name="bt_le_audio_scan_qr_code">Scan QR code</string>
<!-- [CHAR LIMIT=NONE] Le audio QR code scanner sub-title -->
<string name="bt_le_audio_scan_qr_code_scanner">To start listening, center the QR code below</string>
<!-- [CHAR LIMIT=NONE] Hint for QR code process failure -->
<string name="bt_le_audio_qr_code_is_not_valid_format">QR code isn\u0027t a valid format</string>
</resources>

View File

@@ -27,4 +27,16 @@
<item name="android:background">@*android:drawable/btn_borderless_rect</item>
<item name="android:gravity">center</item>
</style>
<style name="TextAppearance.ErrorText"
parent="@*android:TextAppearance.DeviceDefault.Body1">
<item name="android:textColor">?android:attr/colorError</item>
</style>
<style name="QrCodeScanner">
<item name="android:fontFamily">@*android:string/config_headlineFontFamily</item>
<item name="android:textSize">16sp</item>
<item name="android:textColor">?android:attr/textColorPrimary</item>
<item name="android:textDirection">locale</item>
</style>
</resources>

View File

@@ -18,7 +18,32 @@ package com.android.settingslib.bluetooth;
public final class BluetoothBroadcastUtils {
static final String SCHEME_BT_BROADCAST_METADATA = "BT:";
/**
* The fragment tag specified to FragmentManager for container activities to manage fragments.
*/
public static final String TAG_FRAGMENT_QR_CODE_SCANNER = "qr_code_scanner_fragment";
/**
* Action for launching qr code scanner activity.
*/
public static final String ACTION_BLUETOOTH_LE_AUDIO_QR_CODE_SCANNER =
"android.settings.BLUETOOTH_LE_AUDIO_QR_CODE_SCANNER";
/**
* Extra for {@link android.bluetooth.BluetoothDevice}.
*/
public static final String EXTRA_BLUETOOTH_DEVICE_SINK = "bluetooth_device_sink";
/**
* Extra for checking the {@link android.bluetooth.BluetoothLeBroadcastAssistant} should perform
* this operation for all coordinated set members throughout one session or not.
*/
public static final String EXTRA_BLUETOOTH_SINK_IS_GROUP = "bluetooth_sink_is_group";
/**
* Bluetooth scheme.
*/
public static final String SCHEME_BT_BROADCAST_METADATA = "BT:";
// BluetoothLeBroadcastMetadata
static final String PREFIX_BT_ADDRESS_TYPE = "T:";

View File

@@ -19,7 +19,6 @@ package com.android.settingslib.bluetooth;
import android.annotation.NonNull;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothLeBroadcast;
import android.bluetooth.BluetoothLeBroadcastAssistant;
import android.bluetooth.BluetoothLeBroadcastMetadata;
import android.bluetooth.BluetoothLeBroadcastReceiveState;
@@ -71,7 +70,7 @@ public class LocalBluetoothLeBroadcastAssistant implements
}
};
LocalBluetoothLeBroadcastAssistant(Context context,
public LocalBluetoothLeBroadcastAssistant(Context context,
LocalBluetoothProfileManager profileManager) {
mProfileManager = profileManager;
BluetoothAdapter.getDefaultAdapter().
@@ -80,6 +79,40 @@ public class LocalBluetoothLeBroadcastAssistant implements
mBuilder = new BluetoothLeBroadcastMetadata.Builder();
}
/**
* Add a Broadcast Source to the Broadcast Sink with {@link BluetoothLeBroadcastMetadata}.
*
* @param sink Broadcast Sink to which the Broadcast Source should be added
* @param metadata Broadcast Source metadata to be added to the Broadcast Sink
* @param isGroupOp {@code true} if Application wants to perform this operation for all
* coordinated set members throughout this session. Otherwise, caller
* would have to add, modify, and remove individual set members.
*/
public void addSource(BluetoothDevice sink, BluetoothLeBroadcastMetadata metadata,
boolean isGroupOp) {
mBluetoothLeBroadcastAssistant.addSource(sink, metadata, isGroupOp);
}
/**
* Add a Broadcast Source to the Broadcast Sink with the information which are separated from
* the qr code string.
*
* @param sink Broadcast Sink to which the Broadcast Source should be added
* @param sourceAddressType hardware MAC Address of the device. See
* {@link BluetoothDevice.AddressType}.
* @param presentationDelayMicros presentation delay of this Broadcast Source in microseconds.
* @param sourceAdvertisingSid 1-byte long Advertising_SID of the Broadcast Source.
* @param broadcastId 3-byte long Broadcast_ID of the Broadcast Source.
* @param paSyncInterval Periodic Advertising Sync interval of the broadcast Source,
* {@link BluetoothLeBroadcastMetadata#PA_SYNC_INTERVAL_UNKNOWN} if
* unknown.
* @param isEncrypted whether the Broadcast Source is encrypted.
* @param broadcastCode Broadcast Code for this Broadcast Source, null if code is not required.
* @param sourceDevice source advertiser address.
* @param isGroupOp {@code true} if Application wants to perform this operation for all
* coordinated set members throughout this session. Otherwise, caller
* would have to add, modify, and remove individual set members.
*/
public void addSource(@NonNull BluetoothDevice sink, int sourceAddressType,
int presentationDelayMicros, int sourceAdvertisingSid, int broadcastId,
int paSyncInterval, boolean isEncrypted, byte[] broadcastCode,

View File

@@ -83,6 +83,9 @@ public class LocalBluetoothLeBroadcastMetadata {
mSubgroupList = metadata.getSubgroups();
}
public LocalBluetoothLeBroadcastMetadata() {
}
public void setBroadcastCode(byte[] code) {
mBroadcastCode = code;
}