From 13b63904b88adcc8d3937e0b87001fff4a21d676 Mon Sep 17 00:00:00 2001 From: Ze Li Date: Tue, 14 Jan 2025 17:00:43 +0800 Subject: [PATCH 01/14] [Temp bonding] Updater for the guest list to store temp bond device Test: com.android.settings.connecteddevice.audiosharing.TemporaryBondDeviceGroupUpdaterTest Bug: 362859132 Flag: com.android.settingslib.flags.enable_temporary_bond_devices_ui Change-Id: Ic0be83ac0f021988e4c2a2020106055889e3308d --- .../TemporaryBondDeviceGroupUpdater.java | 74 ++++++++++ .../TemporaryBondDeviceGroupUpdaterTest.java | 139 ++++++++++++++++++ 2 files changed, 213 insertions(+) create mode 100644 src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdater.java create mode 100644 tests/robotests/src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdaterTest.java diff --git a/src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdater.java b/src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdater.java new file mode 100644 index 00000000000..59e37c51c08 --- /dev/null +++ b/src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdater.java @@ -0,0 +1,74 @@ +/* + * Copyright (C) 2025 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. + */ + +package com.android.settings.connecteddevice.audiosharing; + +import android.content.Context; +import android.util.Log; + +import androidx.annotation.NonNull; + +import com.android.settings.bluetooth.BluetoothDeviceUpdater; +import com.android.settings.connecteddevice.DevicePreferenceCallback; +import com.android.settingslib.bluetooth.BluetoothUtils; +import com.android.settingslib.bluetooth.CachedBluetoothDevice; +import com.android.settingslib.flags.Flags; + +/** Maintain and update connected temporary bond bluetooth devices */ +public class TemporaryBondDeviceGroupUpdater extends BluetoothDeviceUpdater { + private static final String TAG = "TemporaryBondDeviceGroupUpdater"; + private static final String PREF_KEY_PREFIX = "temp_bond_bt_"; + + public TemporaryBondDeviceGroupUpdater( + @NonNull Context context, + @NonNull DevicePreferenceCallback devicePreferenceCallback, + int metricsCategory) { + super(context, devicePreferenceCallback, metricsCategory); + } + + @Override + public boolean isFilterMatched(@NonNull CachedBluetoothDevice cachedDevice) { + // Only connected temporary bond device should be shown in this section when Audio + // sharing UI is available. + boolean isFilterMatched = Flags.enableTemporaryBondDevicesUi() + && BluetoothUtils.isTemporaryBondDevice(cachedDevice.getDevice()) + && isDeviceConnected(cachedDevice) && isDeviceInCachedDevicesList(cachedDevice) + && BluetoothUtils.isAudioSharingUIAvailable(mContext); + Log.d( + TAG, + "isFilterMatched() device : " + + cachedDevice.getName() + + ", isFilterMatched : " + + isFilterMatched); + return isFilterMatched; + } + + @Override + protected String getPreferenceKeyPrefix() { + return PREF_KEY_PREFIX; + } + + @Override + protected String getLogTag() { + return TAG; + } + + @Override + protected void update(CachedBluetoothDevice cachedBluetoothDevice) { + super.update(cachedBluetoothDevice); + Log.d(TAG, "Map : " + mPreferenceMap); + } +} diff --git a/tests/robotests/src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdaterTest.java b/tests/robotests/src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdaterTest.java new file mode 100644 index 00000000000..0b34c101719 --- /dev/null +++ b/tests/robotests/src/com/android/settings/connecteddevice/audiosharing/TemporaryBondDeviceGroupUpdaterTest.java @@ -0,0 +1,139 @@ +/* + * Copyright (C) 2025 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. + */ + +package com.android.settings.connecteddevice.audiosharing; + +import static com.google.common.truth.Truth.assertThat; + +import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.when; + +import android.bluetooth.BluetoothAdapter; +import android.bluetooth.BluetoothDevice; +import android.bluetooth.BluetoothStatusCodes; +import android.content.Context; +import android.platform.test.annotations.RequiresFlagsEnabled; +import android.platform.test.flag.junit.CheckFlagsRule; +import android.platform.test.flag.junit.DeviceFlagsValueProvider; + +import androidx.test.core.app.ApplicationProvider; + +import com.android.settings.bluetooth.Utils; +import com.android.settings.connecteddevice.DevicePreferenceCallback; +import com.android.settings.testutils.shadow.ShadowBluetoothAdapter; +import com.android.settings.testutils.shadow.ShadowBluetoothUtils; +import com.android.settingslib.bluetooth.CachedBluetoothDevice; +import com.android.settingslib.bluetooth.CachedBluetoothDeviceManager; +import com.android.settingslib.bluetooth.LocalBluetoothManager; +import com.android.settingslib.flags.Flags; + +import org.junit.After; +import org.junit.Before; +import org.junit.Rule; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.Mock; +import org.mockito.MockitoAnnotations; +import org.robolectric.RobolectricTestRunner; +import org.robolectric.annotation.Config; +import org.robolectric.shadow.api.Shadow; + +import java.util.ArrayList; +import java.util.Collection; + +/** Tests for {@link TemporaryBondDeviceGroupUpdater}. */ +@RunWith(RobolectricTestRunner.class) +@Config( + shadows = { + ShadowBluetoothAdapter.class, + ShadowBluetoothUtils.class + }) +public class TemporaryBondDeviceGroupUpdaterTest { + private static final String TAG = "TemporaryBondDeviceGroupUpdater"; + private static final String PREF_KEY_PREFIX = "temp_bond_bt_"; + private static final String TEMP_BOND_METADATA = + "le_audio_sharing"; + private static final int METADATA_FAST_PAIR_CUSTOMIZED_FIELDS = 25; + + @Rule + public final CheckFlagsRule mCheckFlagsRule = DeviceFlagsValueProvider.createCheckFlagsRule(); + + @Mock + private DevicePreferenceCallback mDevicePreferenceCallback; + @Mock + private CachedBluetoothDevice mCachedBluetoothDevice; + @Mock + private BluetoothDevice mBluetoothDevice; + @Mock + private LocalBluetoothManager mLocalBtManager; + @Mock + private CachedBluetoothDeviceManager mCachedDeviceManager; + + private TemporaryBondDeviceGroupUpdater mDeviceUpdater; + + @Before + public void setUp() { + MockitoAnnotations.initMocks(this); + + ShadowBluetoothAdapter shadowBluetoothAdapter = Shadow.extract( + BluetoothAdapter.getDefaultAdapter()); + shadowBluetoothAdapter.setEnabled(true); + shadowBluetoothAdapter.setIsLeAudioBroadcastSourceSupported( + BluetoothStatusCodes.FEATURE_SUPPORTED); + shadowBluetoothAdapter.setIsLeAudioBroadcastAssistantSupported( + BluetoothStatusCodes.FEATURE_SUPPORTED); + Context context = ApplicationProvider.getApplicationContext(); + ShadowBluetoothUtils.sLocalBluetoothManager = mLocalBtManager; + mLocalBtManager = Utils.getLocalBtManager(context); + when(mLocalBtManager.getCachedDeviceManager()).thenReturn(mCachedDeviceManager); + when(mCachedBluetoothDevice.getDevice()).thenReturn(mBluetoothDevice); + Collection cachedDevices = new ArrayList<>(); + cachedDevices.add(mCachedBluetoothDevice); + when(mCachedDeviceManager.getCachedDevicesCopy()).thenReturn(cachedDevices); + mDeviceUpdater = + spy( + new TemporaryBondDeviceGroupUpdater( + context, mDevicePreferenceCallback, /* metricsCategory= */ 0)); + mDeviceUpdater.setPrefContext(context); + } + + @After + public void tearDown() { + ShadowBluetoothUtils.reset(); + } + + @Test + @RequiresFlagsEnabled({Flags.FLAG_ENABLE_TEMPORARY_BOND_DEVICES_UI, + Flags.FLAG_ENABLE_LE_AUDIO_SHARING}) + public void isFilterMatched_isTemporaryBondDevice_returnsTrue() { + when(mBluetoothDevice.isConnected()).thenReturn(true); + when(mBluetoothDevice.getBondState()).thenReturn(BluetoothDevice.BOND_BONDED); + when(mBluetoothDevice.getMetadata(METADATA_FAST_PAIR_CUSTOMIZED_FIELDS)) + .thenReturn(TEMP_BOND_METADATA.getBytes()); + + assertThat(mDeviceUpdater.isFilterMatched(mCachedBluetoothDevice)).isTrue(); + } + + @Test + public void getLogTag_returnsCorrectTag() { + assertThat(mDeviceUpdater.getLogTag()).isEqualTo(TAG); + } + + @Test + public void getPreferenceKey_returnsCorrectKey() { + assertThat(mDeviceUpdater.getPreferenceKeyPrefix()).isEqualTo(PREF_KEY_PREFIX); + } +} From 4de40b3959aea0e6537707a1b711fc4b805e6c62 Mon Sep 17 00:00:00 2001 From: Wenyu Zhang Date: Thu, 16 Jan 2025 13:11:46 +0000 Subject: [PATCH 02/14] a11y: Hook ignore minor cursor movement setting to its controller Change-Id: I2c0ac1c36cc600f551d2a89ab3ec6d1405ac58d9 Test: ToggleAutoclickIgnoreMinorCursorMovementControllerTest Bug: b/388845718 Flag: com.android.server.accessibility.enable_autoclick_indicator --- ...ckIgnoreMinorCursorMovementController.java | 23 +++++++++++++-- ...noreMinorCursorMovementControllerTest.java | 28 +++++++++++++++++++ 2 files changed, 48 insertions(+), 3 deletions(-) diff --git a/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementController.java b/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementController.java index 302e42a2b2f..d5d4fddeaff 100644 --- a/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementController.java +++ b/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementController.java @@ -16,7 +16,14 @@ package com.android.settings.accessibility; +import static android.view.accessibility.AccessibilityManager.AUTOCLICK_IGNORE_MINOR_CURSOR_MOVEMENT_DEFAULT; + +import static com.android.settings.accessibility.AccessibilityUtil.State.OFF; +import static com.android.settings.accessibility.AccessibilityUtil.State.ON; + +import android.content.ContentResolver; import android.content.Context; +import android.provider.Settings; import androidx.annotation.NonNull; @@ -29,9 +36,13 @@ public class ToggleAutoclickIgnoreMinorCursorMovementController extends TogglePr private static final String TAG = ToggleAutoclickIgnoreMinorCursorMovementController.class.getSimpleName(); + private final ContentResolver mContentResolver; + public ToggleAutoclickIgnoreMinorCursorMovementController( @NonNull Context context, @NonNull String key) { super(context, key); + + mContentResolver = context.getContentResolver(); } @Override @@ -41,13 +52,19 @@ public class ToggleAutoclickIgnoreMinorCursorMovementController extends TogglePr @Override public boolean isChecked() { - // TODO(b/388845718): retrieve check status from settings. - return false; + return Settings.Secure.getInt( + mContentResolver, + Settings.Secure.ACCESSIBILITY_AUTOCLICK_IGNORE_MINOR_CURSOR_MOVEMENT, + AUTOCLICK_IGNORE_MINOR_CURSOR_MOVEMENT_DEFAULT ? ON : OFF) + == ON; } @Override public boolean setChecked(boolean isChecked) { - // TODO(b/388845718): Update settings. + Settings.Secure.putInt( + mContentResolver, + Settings.Secure.ACCESSIBILITY_AUTOCLICK_IGNORE_MINOR_CURSOR_MOVEMENT, + isChecked ? ON : OFF); return true; } diff --git a/tests/robotests/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementControllerTest.java b/tests/robotests/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementControllerTest.java index 889b7322888..552e89742b4 100644 --- a/tests/robotests/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementControllerTest.java +++ b/tests/robotests/src/com/android/settings/accessibility/ToggleAutoclickIgnoreMinorCursorMovementControllerTest.java @@ -16,12 +16,17 @@ package com.android.settings.accessibility; +import static android.view.accessibility.AccessibilityManager.AUTOCLICK_IGNORE_MINOR_CURSOR_MOVEMENT_DEFAULT; + +import static com.android.settings.accessibility.AccessibilityUtil.State.OFF; +import static com.android.settings.accessibility.AccessibilityUtil.State.ON; import static com.google.common.truth.Truth.assertThat; import android.content.Context; import android.platform.test.annotations.DisableFlags; import android.platform.test.annotations.EnableFlags; import android.platform.test.flag.junit.SetFlagsRule; +import android.provider.Settings; import androidx.test.core.app.ApplicationProvider; @@ -66,4 +71,27 @@ public class ToggleAutoclickIgnoreMinorCursorMovementControllerTest { assertThat(mController.getAvailabilityStatus()) .isEqualTo(BasePreferenceController.CONDITIONALLY_UNAVAILABLE); } + + @Test + public void isChecked_matchesSetting() { + assertThat(mController.isChecked()).isEqualTo(readSetting() == ON); + } + + @Test + public void setChecked_true_updatesSetting() { + mController.setChecked(true); + assertThat(readSetting()).isEqualTo(ON); + } + + @Test + public void setChecked_false_updatesSetting() { + mController.setChecked(false); + assertThat(readSetting()).isEqualTo(OFF); + } + + private int readSetting() { + return Settings.Secure.getInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_AUTOCLICK_IGNORE_MINOR_CURSOR_MOVEMENT, + AUTOCLICK_IGNORE_MINOR_CURSOR_MOVEMENT_DEFAULT ? ON : OFF); + } } From a7e709c07c7eaec42adc9a630b5b89b258a8b0d5 Mon Sep 17 00:00:00 2001 From: Beth Thibodeau Date: Thu, 16 Jan 2025 09:12:34 -0600 Subject: [PATCH 03/14] Remove MEDIA_CONTROLS_RECOMMENDATION setting toggle Bug: 382680767 Flag: EXEMPT removing deprecated code Test: build, check media settings page Change-Id: I6beaafc7b33e4cb0b29c89cc07ce421c32bf4563 --- res/values/strings.xml | 4 - res/xml/media_controls_settings.xml | 6 -- ...MediaControlsRecommendationController.java | 59 ------------ ...aControlsRecommendationControllerTest.java | 90 ------------------- 4 files changed, 159 deletions(-) delete mode 100644 src/com/android/settings/sound/MediaControlsRecommendationController.java delete mode 100644 tests/unit/src/com/android/settings/sound/MediaControlsRecommendationControllerTest.java diff --git a/res/values/strings.xml b/res/values/strings.xml index 69ff0f10a6a..3e2f2833750 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -13096,10 +13096,6 @@ Show media on lock screen To quickly resume playback, media player stays open on lock screen - - Show Assistant media recommendations - - Based on your activity Hide player diff --git a/res/xml/media_controls_settings.xml b/res/xml/media_controls_settings.xml index 96a2ee442b0..ad5ceb24cd9 100644 --- a/res/xml/media_controls_settings.xml +++ b/res/xml/media_controls_settings.xml @@ -33,10 +33,4 @@ android:summary="@string/media_controls_lockscreen_description" app:controller="com.android.settings.sound.MediaControlsLockScreenPreferenceController" /> - - diff --git a/src/com/android/settings/sound/MediaControlsRecommendationController.java b/src/com/android/settings/sound/MediaControlsRecommendationController.java deleted file mode 100644 index 842a1417a15..00000000000 --- a/src/com/android/settings/sound/MediaControlsRecommendationController.java +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright (C) 2021 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. - */ - -package com.android.settings.sound; - -import static android.provider.Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION; - -import android.content.Context; -import android.provider.Settings; - -import com.android.settings.R; -import com.android.settings.core.TogglePreferenceController; - -/** - * Toggle for media controls recommendation setting - */ -public class MediaControlsRecommendationController extends TogglePreferenceController { - - public MediaControlsRecommendationController(Context context, String key) { - super(context, key); - } - - @Override - public boolean isChecked() { - int val = Settings.Secure.getInt(mContext.getContentResolver(), - MEDIA_CONTROLS_RECOMMENDATION, 1); - return val == 1; - } - - @Override - public boolean setChecked(boolean isChecked) { - int val = isChecked ? 1 : 0; - return Settings.Secure.putInt(mContext.getContentResolver(), - MEDIA_CONTROLS_RECOMMENDATION, val); - } - - @Override - public int getAvailabilityStatus() { - return AVAILABLE; - } - - @Override - public int getSliceHighlightMenuRes() { - return R.string.menu_key_sound; - } -} diff --git a/tests/unit/src/com/android/settings/sound/MediaControlsRecommendationControllerTest.java b/tests/unit/src/com/android/settings/sound/MediaControlsRecommendationControllerTest.java deleted file mode 100644 index 68170b24af8..00000000000 --- a/tests/unit/src/com/android/settings/sound/MediaControlsRecommendationControllerTest.java +++ /dev/null @@ -1,90 +0,0 @@ -/* - * Copyright (C) 2020 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. - */ - -package com.android.settings.sound; - -import static com.android.settings.core.BasePreferenceController.AVAILABLE; - -import static com.google.common.truth.Truth.assertThat; - -import static org.mockito.Mockito.spy; - -import android.content.ContentResolver; -import android.content.Context; -import android.provider.Settings; - -import androidx.test.core.app.ApplicationProvider; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import org.junit.After; -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; - -@RunWith(AndroidJUnit4.class) -public class MediaControlsRecommendationControllerTest { - - private static final String KEY = "media_controls_recommendations"; - - private Context mContext; - private int mOriginalRecommendation; - private ContentResolver mContentResolver; - private MediaControlsRecommendationController mController; - - @Before - public void setUp() { - mContext = spy(ApplicationProvider.getApplicationContext()); - mContentResolver = mContext.getContentResolver(); - mOriginalRecommendation = Settings.Secure.getInt(mContentResolver, - Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, 1); - mController = new MediaControlsRecommendationController(mContext, KEY); - } - - @After - public void tearDown() { - Settings.Secure.putInt(mContentResolver, Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, - mOriginalRecommendation); - } - - @Test - public void getAvailability_returnAvailable() { - assertThat(mController.getAvailabilityStatus()).isEqualTo(AVAILABLE); - } - - @Test - public void setChecked_enable_shouldTurnOn() { - Settings.Secure.putInt(mContentResolver, Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, 1); - - assertThat(mController.isChecked()).isTrue(); - - mController.setChecked(false); - - assertThat(Settings.Secure.getInt(mContentResolver, - Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, -1)).isEqualTo(0); - } - - @Test - public void setChecked_disable_shouldTurnOff() { - Settings.Secure.putInt(mContentResolver, Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, 0); - - assertThat(mController.isChecked()).isFalse(); - - mController.setChecked(true); - - assertThat(Settings.Secure.getInt(mContentResolver, - Settings.Secure.MEDIA_CONTROLS_RECOMMENDATION, -1)).isEqualTo(1); - } -} From 50577a6c36d33830acd809ddbc519ae0f02fa283 Mon Sep 17 00:00:00 2001 From: Yining Liu Date: Thu, 9 Jan 2025 01:37:55 +0000 Subject: [PATCH 04/14] Notification on lockscreen settings: add WhatToShowController Add WhatToShowController to handle the visibility change of the preference category when the global setting changes. Bug: 367455695 Flag: com.android.server.notification.notification_lock_screen_settings Test: manual Change-Id: I432e4c865402ac8bee32f0f79b3cf2bdce7cc882 --- .../lock_screen_notifications_settings.xml | 3 +- .../LockScreenWhatToShowController.java | 101 ++++++++++++++++++ .../LockScreenWhatToShowControllerTest.java | 100 +++++++++++++++++ 3 files changed, 203 insertions(+), 1 deletion(-) create mode 100644 src/com/android/settings/notification/LockScreenWhatToShowController.java create mode 100644 tests/robotests/src/com/android/settings/notification/LockScreenWhatToShowControllerTest.java diff --git a/res/xml/lock_screen_notifications_settings.xml b/res/xml/lock_screen_notifications_settings.xml index e870143823d..52ae18f3f51 100644 --- a/res/xml/lock_screen_notifications_settings.xml +++ b/res/xml/lock_screen_notifications_settings.xml @@ -46,7 +46,8 @@ + android:title="@string/lockscreen_notification_what_to_show_title" + settings:controller="com.android.settings.notification.LockScreenWhatToShowController"> Date: Tue, 14 Jan 2025 21:53:22 +0000 Subject: [PATCH 05/14] a11y: Make images optional for single choice list view dialog This makes `ItemInfoArrayAdapter.ItemInfo` support text-only choices. It is to better accommodate the new dialogs. Bug: b/389991440 Flag: com.android.settings.accessibility.enable_magnification_cursor_following_dialog Test: None Change-Id: If7514631a72631cf0fce85623fe30c8261f678c9 --- .../accessibility/ItemInfoArrayAdapter.java | 20 ++++++++++++------- 1 file changed, 13 insertions(+), 7 deletions(-) diff --git a/src/com/android/settings/accessibility/ItemInfoArrayAdapter.java b/src/com/android/settings/accessibility/ItemInfoArrayAdapter.java index a7c41771cea..285a52b1b9c 100644 --- a/src/com/android/settings/accessibility/ItemInfoArrayAdapter.java +++ b/src/com/android/settings/accessibility/ItemInfoArrayAdapter.java @@ -60,12 +60,17 @@ public class ItemInfoArrayAdapter exten summary.setVisibility(View.GONE); } final ImageView image = root.findViewById(R.id.image); - image.setImageResource(item.mDrawableId); - if (getContext().getResources().getConfiguration().getLayoutDirection() - == View.LAYOUT_DIRECTION_LTR) { - image.setScaleType(ImageView.ScaleType.FIT_START); + if (item.mDrawableId == null) { + image.setVisibility(View.GONE); } else { - image.setScaleType(ImageView.ScaleType.FIT_END); + image.setVisibility(View.VISIBLE); + image.setImageResource(item.mDrawableId); + if (getContext().getResources().getConfiguration().getLayoutDirection() + == View.LAYOUT_DIRECTION_LTR) { + image.setScaleType(ImageView.ScaleType.FIT_START); + } else { + image.setScaleType(ImageView.ScaleType.FIT_END); + } } return root; } @@ -78,11 +83,12 @@ public class ItemInfoArrayAdapter exten public final CharSequence mTitle; @Nullable public final CharSequence mSummary; + @Nullable @DrawableRes - public final int mDrawableId; + public final Integer mDrawableId; public ItemInfo(@NonNull CharSequence title, @Nullable CharSequence summary, - @DrawableRes int drawableId) { + @Nullable @DrawableRes Integer drawableId) { mTitle = title; mSummary = summary; mDrawableId = drawableId; From ab58cb91a9158a973dca37e2ae70a75a90d29b5b Mon Sep 17 00:00:00 2001 From: Joshua McCloskey Date: Wed, 15 Jan 2025 21:31:46 +0000 Subject: [PATCH 06/14] Pattern a11y fix Test: Verified that the next button is no longer disabled, user can click it Fixes: 376175416 Flag: EXEMPT bugfix Change-Id: I30fd80d96b8702e1c8b4bc50dad4c486b220a531 --- src/com/android/settings/password/ChooseLockPattern.java | 4 ++-- .../android/settings/password/SetupChooseLockPatternTest.java | 2 -- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/src/com/android/settings/password/ChooseLockPattern.java b/src/com/android/settings/password/ChooseLockPattern.java index 9680d5a2748..c455a0a9301 100644 --- a/src/com/android/settings/password/ChooseLockPattern.java +++ b/src/com/android/settings/password/ChooseLockPattern.java @@ -348,9 +348,9 @@ public class ChooseLockPattern extends SettingsActivity { */ enum RightButtonMode { Continue(R.string.next_label, true), - ContinueDisabled(R.string.next_label, false), + ContinueDisabled(R.string.next_label, true), Confirm(R.string.lockpattern_confirm_button_text, true), - ConfirmDisabled(R.string.lockpattern_confirm_button_text, false), + ConfirmDisabled(R.string.lockpattern_confirm_button_text, true), Ok(android.R.string.ok, true); /** diff --git a/tests/robotests/src/com/android/settings/password/SetupChooseLockPatternTest.java b/tests/robotests/src/com/android/settings/password/SetupChooseLockPatternTest.java index be3b63bf805..1d42495d077 100644 --- a/tests/robotests/src/com/android/settings/password/SetupChooseLockPatternTest.java +++ b/tests/robotests/src/com/android/settings/password/SetupChooseLockPatternTest.java @@ -287,7 +287,6 @@ public class SetupChooseLockPatternTest { final FooterButton nextButton = footerBarMixin.getPrimaryButton(); assertThat(nextButton.getVisibility()).isEqualTo(View.VISIBLE); - assertThat(nextButton.isEnabled()).isFalse(); enterPattern(); @@ -333,7 +332,6 @@ public class SetupChooseLockPatternTest { mContext.getString(R.string.lockpattern_need_to_unlock_wrong)); assertThat(nextButton.getText().toString()).isEqualTo( mContext.getString(R.string.lockpattern_confirm_button_text)); - assertThat(nextButton.isEnabled()).isFalse(); } @Test From c0d57d06b7fe40579a7730eecd381102a7c5db99 Mon Sep 17 00:00:00 2001 From: Daniel Norman Date: Thu, 16 Jan 2025 20:13:33 +0000 Subject: [PATCH 07/14] Update HCT strings to Text outlines after UXW feedback. Fix: 384791485 Test: see screenshots in bug Flag: EXEMPT resource only strings change Change-Id: I8f3f5bdd93cc13b308b155e45e2ea97e03257abc --- res/values/strings.xml | 8 +++++--- res/xml/accessibility_text_reading_options.xml | 3 ++- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/res/values/strings.xml b/res/values/strings.xml index 236959d2530..f7bc4f164c6 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -5473,11 +5473,11 @@ High contrast text has been replaced - Try Maximize text contrast instead. Find it in Settings. + Try Text outlines instead. Find it in Settings. Open Settings - - Maximize text contrast + + Text outlines Add a black or white background around text to increase contrast @@ -5959,6 +5959,8 @@ screen size, large screen High contrast, low vision, bold font, bold face + + high contrast text diff --git a/res/xml/accessibility_text_reading_options.xml b/res/xml/accessibility_text_reading_options.xml index 40201f0318d..30594fc4730 100644 --- a/res/xml/accessibility_text_reading_options.xml +++ b/res/xml/accessibility_text_reading_options.xml @@ -57,7 +57,8 @@ android:key="toggle_high_text_contrast_preference" android:persistent="false" android:title="@string/accessibility_toggle_maximize_text_contrast_preference_title" - android:summary="@string/accessibility_toggle_maximize_text_contrast_preference_summary" /> + android:summary="@string/accessibility_toggle_maximize_text_contrast_preference_summary" + settings:keywords="@string/keywords_maximize_text_contrast"/> Date: Thu, 16 Jan 2025 15:08:35 +0800 Subject: [PATCH 08/14] [Catalyst] Remove PreferenceMetadata usages Classes that implement PersistentPreference don't need to implement PreferenceMetadata Bug: 388167302 Test: atest and manual Flag: EXEMPT refactor NO_IFTTT=refactor Change-Id: Icf7d5eb4bbd426eb7e8dd562eda3c0a775457a3e --- src/com/android/settings/display/AdaptiveSleepPreference.kt | 4 ++-- .../android/settings/display/BrightnessLevelPreference.kt | 1 - .../android/settings/fuelgauge/BatteryHeaderPreference.kt | 1 - .../android/settings/notification/CallVolumePreference.kt | 1 - .../android/settings/notification/MediaVolumePreference.kt | 1 - .../settings/notification/SeparateRingVolumePreference.kt | 1 - src/com/android/settings/widget/MainSwitchBarMetadata.kt | 6 +++--- .../wifi/calling/WifiCallingMainSwitchPreference.kt | 6 +++--- 8 files changed, 8 insertions(+), 13 deletions(-) diff --git a/src/com/android/settings/display/AdaptiveSleepPreference.kt b/src/com/android/settings/display/AdaptiveSleepPreference.kt index 0fe2a098734..45b05ec3471 100644 --- a/src/com/android/settings/display/AdaptiveSleepPreference.kt +++ b/src/com/android/settings/display/AdaptiveSleepPreference.kt @@ -33,18 +33,18 @@ import com.android.settingslib.datastore.KeyValueStore import com.android.settingslib.datastore.KeyedObservableDelegate import com.android.settingslib.datastore.SettingsSecureStore import com.android.settingslib.datastore.SettingsStore +import com.android.settingslib.metadata.BooleanValuePreference import com.android.settingslib.metadata.PreferenceAvailabilityProvider import com.android.settingslib.metadata.PreferenceLifecycleContext import com.android.settingslib.metadata.PreferenceLifecycleProvider import com.android.settingslib.metadata.ReadWritePermit import com.android.settingslib.metadata.SensitivityLevel -import com.android.settingslib.metadata.TwoStatePreference import com.android.settingslib.preference.PreferenceBindingPlaceholder import com.android.settingslib.preference.SwitchPreferenceBinding // LINT.IfChange class AdaptiveSleepPreference : - TwoStatePreference, + BooleanValuePreference, SwitchPreferenceBinding, PreferenceLifecycleProvider, PreferenceBindingPlaceholder, // not needed once controller class is cleaned up diff --git a/src/com/android/settings/display/BrightnessLevelPreference.kt b/src/com/android/settings/display/BrightnessLevelPreference.kt index e14db6b59a6..0465d22361e 100644 --- a/src/com/android/settings/display/BrightnessLevelPreference.kt +++ b/src/com/android/settings/display/BrightnessLevelPreference.kt @@ -55,7 +55,6 @@ import java.text.NumberFormat // LINT.IfChange class BrightnessLevelPreference : - PreferenceMetadata, PersistentPreference, RangeValue, PreferenceBinding, diff --git a/src/com/android/settings/fuelgauge/BatteryHeaderPreference.kt b/src/com/android/settings/fuelgauge/BatteryHeaderPreference.kt index f0a3ae67af9..36654691c36 100644 --- a/src/com/android/settings/fuelgauge/BatteryHeaderPreference.kt +++ b/src/com/android/settings/fuelgauge/BatteryHeaderPreference.kt @@ -39,7 +39,6 @@ import com.android.settingslib.widget.UsageProgressBarPreference // LINT.IfChange class BatteryHeaderPreference : PersistentPreference, - PreferenceMetadata, PreferenceBinding, PreferenceLifecycleProvider, RangeValue { diff --git a/src/com/android/settings/notification/CallVolumePreference.kt b/src/com/android/settings/notification/CallVolumePreference.kt index 3caac242316..cc6f45fe270 100644 --- a/src/com/android/settings/notification/CallVolumePreference.kt +++ b/src/com/android/settings/notification/CallVolumePreference.kt @@ -43,7 +43,6 @@ import com.android.settingslib.preference.PreferenceBinding // LINT.IfChange open class CallVolumePreference : - PreferenceMetadata, PreferenceBinding, PersistentPreference, RangeValue, diff --git a/src/com/android/settings/notification/MediaVolumePreference.kt b/src/com/android/settings/notification/MediaVolumePreference.kt index 02bf82479c0..71f2f91276f 100644 --- a/src/com/android/settings/notification/MediaVolumePreference.kt +++ b/src/com/android/settings/notification/MediaVolumePreference.kt @@ -40,7 +40,6 @@ import com.android.settingslib.preference.PreferenceBinding // LINT.IfChange open class MediaVolumePreference : - PreferenceMetadata, PreferenceBinding, PersistentPreference, RangeValue, diff --git a/src/com/android/settings/notification/SeparateRingVolumePreference.kt b/src/com/android/settings/notification/SeparateRingVolumePreference.kt index 4cdac1434bf..7bc39a82d10 100644 --- a/src/com/android/settings/notification/SeparateRingVolumePreference.kt +++ b/src/com/android/settings/notification/SeparateRingVolumePreference.kt @@ -58,7 +58,6 @@ import com.android.settingslib.preference.PreferenceBinding // LINT.IfChange open class SeparateRingVolumePreference : - PreferenceMetadata, PreferenceBinding, PersistentPreference, RangeValue, diff --git a/src/com/android/settings/widget/MainSwitchBarMetadata.kt b/src/com/android/settings/widget/MainSwitchBarMetadata.kt index 4fc89bc19b6..0f07bba3eaa 100644 --- a/src/com/android/settings/widget/MainSwitchBarMetadata.kt +++ b/src/com/android/settings/widget/MainSwitchBarMetadata.kt @@ -18,14 +18,14 @@ package com.android.settings.widget import android.content.Context import androidx.preference.Preference +import com.android.settingslib.metadata.BooleanValuePreference import com.android.settingslib.metadata.PreferenceMetadata -import com.android.settingslib.metadata.TwoStatePreference import com.android.settingslib.preference.PreferenceBindingPlaceholder -import com.android.settingslib.preference.TwoStatePreferenceBinding +import com.android.settingslib.preference.BooleanValuePreferenceBinding /** Base metadata of `MainSwitchBar`. */ interface MainSwitchBarMetadata : - TwoStatePreference, TwoStatePreferenceBinding, PreferenceBindingPlaceholder { + BooleanValuePreference, BooleanValuePreferenceBinding, PreferenceBindingPlaceholder { /** * Disable main switch bar when user toggles the switch. By this way, user cannot toggle again diff --git a/src/com/android/settings/wifi/calling/WifiCallingMainSwitchPreference.kt b/src/com/android/settings/wifi/calling/WifiCallingMainSwitchPreference.kt index dc6737310d3..8765547a957 100644 --- a/src/com/android/settings/wifi/calling/WifiCallingMainSwitchPreference.kt +++ b/src/com/android/settings/wifi/calling/WifiCallingMainSwitchPreference.kt @@ -33,11 +33,11 @@ import com.android.settingslib.datastore.KeyValueStore import com.android.settingslib.datastore.NoOpKeyedObservable import com.android.settingslib.datastore.Permissions import com.android.settingslib.datastore.and +import com.android.settingslib.metadata.BooleanValuePreference import com.android.settingslib.metadata.PreferenceAvailabilityProvider import com.android.settingslib.metadata.ReadWritePermit import com.android.settingslib.metadata.SensitivityLevel -import com.android.settingslib.metadata.TwoStatePreference -import com.android.settingslib.preference.TwoStatePreferenceBinding +import com.android.settingslib.preference.BooleanValuePreferenceBinding import kotlinx.coroutines.flow.first import kotlinx.coroutines.runBlocking @@ -47,7 +47,7 @@ import kotlinx.coroutines.runBlocking * TODO(b/372732219): apply metadata to UI */ class WifiCallingMainSwitchPreference(private val subId: Int) : - TwoStatePreference, TwoStatePreferenceBinding, PreferenceAvailabilityProvider { + BooleanValuePreference, BooleanValuePreferenceBinding, PreferenceAvailabilityProvider { override val key: String get() = KEY From 081836703a3f7a3b23dd2243ea30346e58b16938 Mon Sep 17 00:00:00 2001 From: Lorenzo Lucena Maguire Date: Wed, 15 Jan 2025 21:26:41 +0000 Subject: [PATCH 09/14] Create Double Tap Power Settings Activity Test: manually launched activity Bug: 390257067 Flag: EXEMPT declared activity in xml Change-Id: Idc858b4e916df7e716790b7297b1bd5a58874452 --- AndroidManifest.xml | 17 +++++++++++++++++ src/com/android/settings/Settings.java | 5 +++++ 2 files changed, 22 insertions(+) diff --git a/AndroidManifest.xml b/AndroidManifest.xml index bce30dc7068..f2638c74414 100644 --- a/AndroidManifest.xml +++ b/AndroidManifest.xml @@ -5301,6 +5301,23 @@ android:value="true" /> + + + + + + + + + + diff --git a/src/com/android/settings/Settings.java b/src/com/android/settings/Settings.java index 91494af29c6..ee866babffc 100644 --- a/src/com/android/settings/Settings.java +++ b/src/com/android/settings/Settings.java @@ -518,6 +518,11 @@ public class Settings extends SettingsActivity { */ public static class OneHandedSettingsActivity extends SettingsActivity { /* empty */ } + /** + * Activity for Double Tap Power Settings + */ + public static class DoubleTapPowerSettingsActivity extends SettingsActivity { /* empty */ } + public static class PreviouslyConnectedDeviceActivity extends SettingsActivity { /* empty */ } public static class ScreenTimeoutActivity extends SettingsActivity { /* empty */ } From 68178f684ebf811a6d9bad9fa617ae681cd9164f Mon Sep 17 00:00:00 2001 From: Jacky Wang Date: Fri, 17 Jan 2025 16:02:50 +0800 Subject: [PATCH 10/14] [Catalyst] Refine AmbientDisplayAlwaysOnPreference datastore NO_IFTTT=Catalyst only Bug: 372307567 Flag: com.android.settings.flags.catalyst_lockscreen_from_display_settings Test: devtool Change-Id: Icd7990d4bb42c2ed5e3432d0dd81473217913b56 --- .../AmbientDisplayAlwaysOnPreference.kt | 42 ++++++++++--------- 1 file changed, 22 insertions(+), 20 deletions(-) diff --git a/src/com/android/settings/display/AmbientDisplayAlwaysOnPreference.kt b/src/com/android/settings/display/AmbientDisplayAlwaysOnPreference.kt index 2d2fe2b2d70..3cc608bec91 100644 --- a/src/com/android/settings/display/AmbientDisplayAlwaysOnPreference.kt +++ b/src/com/android/settings/display/AmbientDisplayAlwaysOnPreference.kt @@ -25,15 +25,13 @@ import android.provider.Settings.Secure.DOZE_ALWAYS_ON import com.android.settings.PreferenceRestrictionMixin import com.android.settings.R import com.android.settings.display.AmbientDisplayAlwaysOnPreferenceController.isAodSuppressedByBedtime +import com.android.settingslib.datastore.AbstractKeyedDataObservable import com.android.settingslib.datastore.HandlerExecutor import com.android.settingslib.datastore.KeyValueStore -import com.android.settingslib.datastore.KeyedObservableDelegate import com.android.settingslib.datastore.KeyedObserver import com.android.settingslib.datastore.SettingsSecureStore import com.android.settingslib.datastore.SettingsStore import com.android.settingslib.metadata.PreferenceAvailabilityProvider -import com.android.settingslib.metadata.PreferenceLifecycleContext -import com.android.settingslib.metadata.PreferenceLifecycleProvider import com.android.settingslib.metadata.PreferenceSummaryProvider import com.android.settingslib.metadata.ReadWritePermit import com.android.settingslib.metadata.SensitivityLevel @@ -44,11 +42,8 @@ class AmbientDisplayAlwaysOnPreference : SwitchPreference(KEY, R.string.doze_always_on_title, R.string.doze_always_on_summary), PreferenceAvailabilityProvider, PreferenceSummaryProvider, - PreferenceLifecycleProvider, PreferenceRestrictionMixin { - private var keyMappingObserver: KeyedObserver? = null - override val keywords: Int get() = R.string.keywords_always_show_time_info @@ -88,24 +83,17 @@ class AmbientDisplayAlwaysOnPreference : override val sensitivityLevel get() = SensitivityLevel.NO_SENSITIVITY - override fun onCreate(context: PreferenceLifecycleContext) { - val storage = SettingsSecureStore.get(context) - keyMappingObserver = - KeyedObserver { _, reason -> storage.notifyChange(KEY, reason) } - .also { storage.addObserver(DOZE_ALWAYS_ON, it, HandlerExecutor.main) } - } - - override fun onDestroy(context: PreferenceLifecycleContext) { - keyMappingObserver?.let { - SettingsSecureStore.get(context).removeObserver(DOZE_ALWAYS_ON, it) - } - } - + /** + * Datastore of the preference. + * + * The preference key and underlying storage key are the different, leverage + * [AbstractKeyedDataObservable] to redirect data change event. + */ @Suppress("UNCHECKED_CAST") class Storage( private val context: Context, private val settingsStore: SettingsStore = SettingsSecureStore.get(context), - ) : KeyedObservableDelegate(settingsStore), KeyValueStore { + ) : AbstractKeyedDataObservable(), KeyedObserver, KeyValueStore { override fun contains(key: String) = settingsStore.contains(DOZE_ALWAYS_ON) @@ -118,6 +106,20 @@ class AmbientDisplayAlwaysOnPreference : override fun setValue(key: String, valueType: Class, value: T?) = settingsStore.setValue(DOZE_ALWAYS_ON, valueType, value) + + override fun onFirstObserverAdded() { + // observe the underlying storage key + settingsStore.addObserver(DOZE_ALWAYS_ON, this, HandlerExecutor.main) + } + + override fun onKeyChanged(key: String, reason: Int) { + // forward data change to preference hierarchy key + notifyChange(KEY, reason) + } + + override fun onLastObserverRemoved() { + settingsStore.removeObserver(DOZE_ALWAYS_ON, this) + } } companion object { From 03de6af4fc3839fe390236ae030e35d6d08a9fc2 Mon Sep 17 00:00:00 2001 From: Sunny Shao Date: Fri, 17 Jan 2025 06:16:32 +0000 Subject: [PATCH 11/14] [Catalyst] Rollback the Adaptive brightness key Let the redirect highlight function work from Turbo app. NO_IFTTT=Catalyst migration Test: devtool, atest AutoBrightnessScreenTest Bug: 390525596 Flag: com.android.settings.flags.catalyst_display_settings_screen Change-Id: Id7261d8a51368c45b7e23fee911565a226b30779 --- res/xml/display_settings.xml | 2 +- .../settings/display/AutoBrightnessScreen.kt | 30 ++++++++++++++----- .../display/AutoBrightnessScreenTest.kt | 6 +++- 3 files changed, 29 insertions(+), 9 deletions(-) diff --git a/res/xml/display_settings.xml b/res/xml/display_settings.xml index 3baf439035a..c7e29675757 100644 --- a/res/xml/display_settings.xml +++ b/res/xml/display_settings.xml @@ -34,7 +34,7 @@ settings:userRestriction="no_config_brightness"/> (settingsStore), KeyValueStore { + AbstractKeyedDataObservable(), KeyedObserver, KeyValueStore { - override fun contains(key: String) = settingsStore.contains(key) + override fun contains(key: String) = settingsStore.contains(SCREEN_BRIGHTNESS_MODE) override fun getDefaultValue(key: String, valueType: Class) = DEFAULT_VALUE.toBoolean() as T override fun getValue(key: String, valueType: Class) = - (settingsStore.getInt(key) ?: DEFAULT_VALUE).toBoolean() as T + (settingsStore.getInt(SCREEN_BRIGHTNESS_MODE) ?: DEFAULT_VALUE).toBoolean() as T override fun setValue(key: String, valueType: Class, value: T?) = - settingsStore.setInt(key, (value as? Boolean)?.toBrightnessMode()) + settingsStore.setInt(SCREEN_BRIGHTNESS_MODE, (value as? Boolean)?.toBrightnessMode()) + + override fun onFirstObserverAdded() { + // observe the underlying storage key + settingsStore.addObserver(SCREEN_BRIGHTNESS_MODE, this, HandlerExecutor.main) + } + + override fun onKeyChanged(key: String, reason: Int) { + // forward data change to preference hierarchy key + notifyChange(KEY, reason) + } + + override fun onLastObserverRemoved() { + settingsStore.removeObserver(SCREEN_BRIGHTNESS_MODE, this) + } /** Converts brightness mode integer to boolean. */ private fun Int.toBoolean() = this == SCREEN_BRIGHTNESS_MODE_AUTOMATIC @@ -128,7 +144,7 @@ class AutoBrightnessScreen : } companion object { - const val KEY = Settings.System.SCREEN_BRIGHTNESS_MODE + const val KEY = "auto_brightness_entry" private const val DEFAULT_VALUE = SCREEN_BRIGHTNESS_MODE_MANUAL } } diff --git a/tests/robotests/src/com/android/settings/display/AutoBrightnessScreenTest.kt b/tests/robotests/src/com/android/settings/display/AutoBrightnessScreenTest.kt index ab2d9bd29d9..5da5c2a8a37 100644 --- a/tests/robotests/src/com/android/settings/display/AutoBrightnessScreenTest.kt +++ b/tests/robotests/src/com/android/settings/display/AutoBrightnessScreenTest.kt @@ -128,7 +128,11 @@ class AutoBrightnessScreenTest { } private fun setScreenBrightnessMode(value: Int) = - Settings.System.putInt(context.contentResolver, AutoBrightnessScreen.KEY, value) + Settings.System.putInt( + context.contentResolver, + Settings.System.SCREEN_BRIGHTNESS_MODE, + value, + ) private fun getResId() = when { From 43847455171e47cba9bac7a1e845536d1a3d1144 Mon Sep 17 00:00:00 2001 From: Randy Pfohl Date: Fri, 17 Jan 2025 01:38:48 +0000 Subject: [PATCH 12/14] update string to remove duplicate accessibility readout bug: 386688984 Test: built locally Flag: NONE not needed Change-Id: Ie8e0c25a753bd7dacb9145b58dbffc5f89ff6808 --- res/values/strings.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/res/values/strings.xml b/res/values/strings.xml index 9930c3685c0..6f81a52872f 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -11367,7 +11367,7 @@ Go back, Home, and switch apps with buttons at the bottom of your screen. - Start gesture navigation tutorial, button. Double tap to activate. + Start gesture navigation tutorial. system navigation, 2 button navigation, 3 button navigation, gesture navigation, swipe From f2e29d4359432632c319221b992af110bf04384e Mon Sep 17 00:00:00 2001 From: Joshua McCloskey Date: Thu, 16 Jan 2025 23:03:14 +0000 Subject: [PATCH 13/14] A11y pattern view is no longer selectable Fixes: 386873612 Fixes: 386873927 Test: Verified pattern view is no longer selectable, but cells are still announced. Flag: EXEMPT bugfix Change-Id: If80da276f2a33206c39552b6b86a92c899f865a9 --- src/com/android/settings/password/ChooseLockPattern.java | 1 + 1 file changed, 1 insertion(+) diff --git a/src/com/android/settings/password/ChooseLockPattern.java b/src/com/android/settings/password/ChooseLockPattern.java index c455a0a9301..a30c38b20b8 100644 --- a/src/com/android/settings/password/ChooseLockPattern.java +++ b/src/com/android/settings/password/ChooseLockPattern.java @@ -563,6 +563,7 @@ public class ChooseLockPattern extends SettingsActivity { mLockPatternView = (LockPatternView) view.findViewById(R.id.lockPattern); mLockPatternView.setOnPatternListener(mChooseNewLockPatternListener); mLockPatternView.setFadePattern(false); + mLockPatternView.setClickable(false); mFooterText = (TextView) view.findViewById(R.id.footerText); From 39329c219d0787c0041e34947d17c0747e1aa06b Mon Sep 17 00:00:00 2001 From: Kasia Krejszeff Date: Fri, 13 Dec 2024 16:15:51 +0000 Subject: [PATCH 14/14] Ensure Private profile is present in tests in the FaceFingerprintUnlockControllerTest and re-enable ignored tests. Bug: 323652985 Flag: TEST_ONLY Test: atest FaceFingerprintUnlockControllerTest Change-Id: I0c923a95b8b7cf1320b68818e831dea5bb7510bf --- .../FaceFingerprintUnlockControllerTest.java | 20 ++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) diff --git a/tests/unit/src/com/android/settings/privatespace/FaceFingerprintUnlockControllerTest.java b/tests/unit/src/com/android/settings/privatespace/FaceFingerprintUnlockControllerTest.java index bdeede874fc..ba82e19a6e6 100644 --- a/tests/unit/src/com/android/settings/privatespace/FaceFingerprintUnlockControllerTest.java +++ b/tests/unit/src/com/android/settings/privatespace/FaceFingerprintUnlockControllerTest.java @@ -34,8 +34,8 @@ import com.android.settings.privatespace.onelock.FaceFingerprintUnlockController import com.android.settings.testutils.FakeFeatureFactory; import com.android.settingslib.core.lifecycle.Lifecycle; +import org.junit.After; import org.junit.Before; -import org.junit.Ignore; import org.junit.Rule; import org.junit.Test; import org.junit.runner.RunWith; @@ -51,6 +51,7 @@ public class FaceFingerprintUnlockControllerTest { @Mock LockPatternUtils mLockPatternUtils; private Preference mPreference; + private PrivateSpaceMaintainer mPrivateSpaceMaintainer; private FaceFingerprintUnlockController mFaceFingerprintUnlockController; /** Required setup before a test. */ @@ -68,12 +69,26 @@ public class FaceFingerprintUnlockControllerTest { .thenReturn(mLockPatternUtils); doReturn(true).when(mLockPatternUtils).isSecure(anyInt()); + + mPrivateSpaceMaintainer = PrivateSpaceMaintainer.getInstance(mContext); + assertThat(mPrivateSpaceMaintainer.createPrivateSpace()).isTrue(); + assertThat(mPrivateSpaceMaintainer.doesPrivateSpaceExist()).isTrue(); + mFaceFingerprintUnlockController = new FaceFingerprintUnlockController(mContext, mLifecycle); } + @After + public void tearDown() { + // Ensure PSMaintainer is able to remove PS. + mSetFlagsRule.enableFlags( + android.os.Flags.FLAG_ALLOW_PRIVATE_PROFILE, + android.multiuser.Flags.FLAG_ENABLE_PRIVATE_SPACE_FEATURES); + assertThat(mPrivateSpaceMaintainer.deletePrivateSpace()) + .isEqualTo(PrivateSpaceMaintainer.ErrorDeletingPrivateSpace.DELETE_PS_ERROR_NONE); + } + /** Tests that the controller is always available. */ - @Ignore("b/323652985") @Test public void getAvailabilityStatus_whenFlagsEnabled_returnsAvailable() { mSetFlagsRule.enableFlags( @@ -134,7 +149,6 @@ public class FaceFingerprintUnlockControllerTest { } /** Tests that preference is enabled and summary is not same as device lock. */ - @Ignore("b/323652985") @Test public void getSummary_whenSeparateProfileLock() { doReturn(true).when(mLockPatternUtils).isSeparateProfileChallengeEnabled(anyInt());