diff options
| author | 2024-07-19 05:10:36 +0000 | |
|---|---|---|
| committer | 2024-10-16 18:25:13 +0000 | |
| commit | d5e5c5025bd49f8a6d899ea66e28ae220e7546a7 (patch) | |
| tree | a3e16902d1df76a47feb050c594e2c4f552c971e | |
| parent | 4ba1a4de27823876ac6bc06206c1ad220236673a (diff) | |
Adds SystemUI DeviceStateManager utilities
Adds a DeviceStateManager kosmo that provides helper state
information that can be used in tests.
Also updates the Utils#isFoldable method to use the
updated DeviceState#hasProperty method, to be used by
clients within SystemUI.
Test: UtilsTest
Bug: 336640888
Flag: android.hardware.devicestate.feature.flags.device_state_property_migration
Change-Id: I777f7702df01e34546afb147cf2adda2dd39e0f7
3 files changed, 285 insertions, 3 deletions
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/util/UtilsTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/util/UtilsTest.kt new file mode 100644 index 000000000000..2549b31f7eca --- /dev/null +++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/util/UtilsTest.kt @@ -0,0 +1,126 @@ +/* + * Copyright (C) 2017 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.systemui.util + +import android.hardware.devicestate.DeviceState +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_INNER_PRIMARY +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_CLOSED +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_OPEN +import android.hardware.devicestate.feature.flags.Flags +import android.platform.test.annotations.RequiresFlagsDisabled +import android.platform.test.annotations.RequiresFlagsEnabled +import android.testing.TestableResources +import androidx.test.ext.junit.runners.AndroidJUnit4 +import androidx.test.filters.SmallTest +import com.android.systemui.SysuiTestCase +import com.android.systemui.kosmos.Kosmos +import com.android.systemui.deviceStateManager +import junit.framework.Assert.assertFalse +import junit.framework.Assert.assertTrue +import org.junit.Before +import org.junit.Test +import org.junit.runner.RunWith +import org.mockito.kotlin.whenever + +@SmallTest +@RunWith(AndroidJUnit4::class) +class UtilsTest : SysuiTestCase() { + + private val kosmos = Kosmos() + private val deviceStateManager = kosmos.deviceStateManager + private lateinit var testableResources: TestableResources + + + @Before + fun setUp() { + testableResources = context.orCreateTestableResources + } + + @Test + @RequiresFlagsDisabled(Flags.FLAG_DEVICE_STATE_PROPERTY_MIGRATION) + fun isFoldableReturnsFalse_overlayConfigurationValues() { + testableResources.addOverride( + com.android.internal.R.array.config_foldedDeviceStates, + intArrayOf() // empty array <=> device is not foldable + ) + whenever(deviceStateManager.supportedDeviceStates).thenReturn(listOf(DEFAULT_DEVICE_STATE)) + assertFalse(Utils.isDeviceFoldable(testableResources.resources, deviceStateManager)) + } + + @Test + @RequiresFlagsEnabled(Flags.FLAG_DEVICE_STATE_PROPERTY_MIGRATION) + fun isFoldableReturnsFalse_deviceStateManager() { + testableResources.addOverride( + com.android.internal.R.array.config_foldedDeviceStates, + intArrayOf() // empty array <=> device is not foldable + ) + whenever(deviceStateManager.supportedDeviceStates).thenReturn(listOf(DEFAULT_DEVICE_STATE)) + assertFalse(Utils.isDeviceFoldable(testableResources.resources, deviceStateManager)) + } + + @Test + @RequiresFlagsDisabled(Flags.FLAG_DEVICE_STATE_PROPERTY_MIGRATION) + fun isFoldableReturnsTrue_overlayConfigurationValues() { + testableResources.addOverride( + com.android.internal.R.array.config_foldedDeviceStates, + intArrayOf(FOLDED_DEVICE_STATE.identifier) + ) + whenever(deviceStateManager.supportedDeviceStates).thenReturn( + listOf( + FOLDED_DEVICE_STATE, + UNFOLDED_DEVICE_STATE + ) + ) + assertTrue(Utils.isDeviceFoldable(testableResources.resources, deviceStateManager)) + } + + @Test + @RequiresFlagsEnabled(Flags.FLAG_DEVICE_STATE_PROPERTY_MIGRATION) + fun isFoldableReturnsTrue_deviceStateManager() { + testableResources.addOverride( + com.android.internal.R.array.config_foldedDeviceStates, + intArrayOf(FOLDED_DEVICE_STATE.identifier) + ) + whenever(deviceStateManager.supportedDeviceStates).thenReturn( + listOf( + FOLDED_DEVICE_STATE, + UNFOLDED_DEVICE_STATE + ) + ) + assertTrue(Utils.isDeviceFoldable(testableResources.resources, deviceStateManager)) + } + + companion object { + private val DEFAULT_DEVICE_STATE = DeviceState( + DeviceState.Configuration.Builder( + 0 /* identifier */, "DEFAULT" + ).build() + ) + private val FOLDED_DEVICE_STATE = DeviceState( + DeviceState.Configuration.Builder(1 /* identifier */, "FOLDED") + .setSystemProperties(setOf(PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY)) + .setPhysicalProperties( + setOf(PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_CLOSED) + ).build() + ) + private val UNFOLDED_DEVICE_STATE = DeviceState( + DeviceState.Configuration.Builder(2 /* identifier */, "UNFOLDED") + .setSystemProperties(setOf(PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_INNER_PRIMARY)) + .setPhysicalProperties(setOf(PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_OPEN)) + .build() + ) + } +}
\ No newline at end of file diff --git a/packages/SystemUI/src/com/android/systemui/util/Utils.java b/packages/SystemUI/src/com/android/systemui/util/Utils.java index 3953188bb828..800d2894f192 100644 --- a/packages/SystemUI/src/com/android/systemui/util/Utils.java +++ b/packages/SystemUI/src/com/android/systemui/util/Utils.java @@ -14,11 +14,17 @@ package com.android.systemui.util; +import static android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_INNER_PRIMARY; +import static android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY; + import android.Manifest; import android.content.Context; import android.content.Intent; import android.content.pm.PackageManager; import android.content.res.Resources; +import android.hardware.devicestate.DeviceState; +import android.hardware.devicestate.DeviceStateManager; +import android.hardware.devicestate.feature.flags.Flags; import android.provider.Settings; import android.view.DisplayCutout; @@ -84,9 +90,23 @@ public class Utils { /** * Returns {@code true} if the device is a foldable device */ - public static boolean isDeviceFoldable(Context context) { - return context.getResources() - .getIntArray(com.android.internal.R.array.config_foldedDeviceStates).length != 0; + public static boolean isDeviceFoldable(Resources resources, + DeviceStateManager deviceStateManager) { + if (Flags.deviceStatePropertyMigration()) { + List<DeviceState> deviceStates = deviceStateManager.getSupportedDeviceStates(); + for (int i = 0; i < deviceStates.size(); i++) { + DeviceState state = deviceStates.get(i); + if (state.hasProperty(PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY) + || state.hasProperty( + PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_INNER_PRIMARY)) { + return true; + } + } + return false; + } else { + return resources.getIntArray( + com.android.internal.R.array.config_foldedDeviceStates).length != 0; + } } /** diff --git a/packages/SystemUI/tests/utils/src/com/android/systemui/DeviceStateManagerKosmos.kt b/packages/SystemUI/tests/utils/src/com/android/systemui/DeviceStateManagerKosmos.kt new file mode 100644 index 000000000000..f4a9dc43b46e --- /dev/null +++ b/packages/SystemUI/tests/utils/src/com/android/systemui/DeviceStateManagerKosmos.kt @@ -0,0 +1,136 @@ +/* + * Copyright (C) 2024 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.systemui + +import android.hardware.devicestate.DeviceState +import android.hardware.devicestate.DeviceState.PROPERTY_FEATURE_REAR_DISPLAY +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_INNER_PRIMARY +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_CLOSED +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_HALF_OPEN +import android.hardware.devicestate.DeviceState.PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_OPEN +import android.hardware.devicestate.DeviceState.PROPERTY_POWER_CONFIGURATION_TRIGGER_SLEEP +import android.hardware.devicestate.DeviceState.PROPERTY_POWER_CONFIGURATION_TRIGGER_WAKE +import android.hardware.devicestate.DeviceStateManager +import com.android.systemui.kosmos.Kosmos +import org.mockito.kotlin.mock + +val Kosmos.deviceStateManager by Kosmos.Fixture { mock<DeviceStateManager>() } + +val Kosmos.defaultDeviceState by Kosmos.Fixture { + DeviceState( + DeviceState.Configuration.Builder( + 0 /* identifier */, + "DEFAULT" + ).build() + ) +} + +val Kosmos.foldedDeviceStateList by Kosmos.Fixture { + listOf( + DeviceState( + DeviceState.Configuration.Builder(0, "FOLDED_0") + .setSystemProperties( + setOf( + PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY, + PROPERTY_POWER_CONFIGURATION_TRIGGER_SLEEP + ) + ) + .setPhysicalProperties( + setOf(PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_CLOSED) + ) + .build() + ), + DeviceState( + DeviceState.Configuration.Builder(1, "FOLDED_1") + .setSystemProperties( + setOf( + PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY, + PROPERTY_POWER_CONFIGURATION_TRIGGER_SLEEP + ) + ) + .setPhysicalProperties( + setOf(PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_CLOSED) + ) + .build() + ), + DeviceState( + DeviceState.Configuration.Builder(2, "FOLDED_2") + .setSystemProperties( + setOf( + PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY, + PROPERTY_POWER_CONFIGURATION_TRIGGER_SLEEP + ) + ) + .setPhysicalProperties( + setOf(PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_CLOSED) + ) + .build() + ) + ) +} + +val Kosmos.halfFoldedDeviceState by Kosmos.Fixture { + DeviceState( + DeviceState.Configuration.Builder(3 /* identifier */, "HALF_FOLDED") + .setSystemProperties( + setOf( + PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_INNER_PRIMARY, + PROPERTY_POWER_CONFIGURATION_TRIGGER_WAKE + ) + ) + .setPhysicalProperties( + setOf(PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_HALF_OPEN) + ) + .build() + ) +} + +val Kosmos.unfoldedDeviceState by Kosmos.Fixture { + DeviceState( + DeviceState.Configuration.Builder(4 /* identifier */, "UNFOLDED") + .setSystemProperties( + setOf( + PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_INNER_PRIMARY, + PROPERTY_POWER_CONFIGURATION_TRIGGER_WAKE + ) + ) + .setPhysicalProperties( + setOf(PROPERTY_FOLDABLE_HARDWARE_CONFIGURATION_FOLD_IN_OPEN) + ) + .build() + ) +} + +val Kosmos.rearDisplayDeviceState by Kosmos.Fixture { + DeviceState( + DeviceState.Configuration.Builder(5 /* identifier */, "REAR_DISPLAY") + .setSystemProperties( + setOf( + PROPERTY_FOLDABLE_DISPLAY_CONFIGURATION_OUTER_PRIMARY, + PROPERTY_FEATURE_REAR_DISPLAY + ) + ) + .build() + ) +} + +val Kosmos.unknownDeviceState by Kosmos.Fixture { + DeviceState( + DeviceState.Configuration.Builder(8 /* identifier */, "UNKNOWN").build() + ) +} |