Loading packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/ResponsiveLazyHorizontalGrid.kt +6 −3 Original line number Diff line number Diff line Loading @@ -48,6 +48,9 @@ import androidx.compose.ui.unit.coerceAtMost import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.times import androidx.window.layout.WindowMetricsCalculator import com.android.systemui.communal.util.WindowSizeUtils.COMPACT_HEIGHT import com.android.systemui.communal.util.WindowSizeUtils.COMPACT_WIDTH import com.android.systemui.communal.util.WindowSizeUtils.MEDIUM_WIDTH /** * Renders a responsive [LazyHorizontalGrid] with dynamic columns and rows. Each cell will maintain Loading Loading @@ -266,14 +269,14 @@ fun calculateWindowSize(): DpSize { private fun calculateNumCellsWidth(width: Dp) = // See https://developer.android.com/develop/ui/views/layout/use-window-size-classes when { width >= 840.dp -> 3 width >= 600.dp -> 2 width >= MEDIUM_WIDTH -> 3 width >= COMPACT_WIDTH -> 2 else -> 1 } private fun calculateNumCellsHeight(height: Dp) = when { height >= 1000.dp -> 3 height >= 480.dp -> 2 height >= COMPACT_HEIGHT -> 2 else -> 1 } packages/SystemUI/multivalentTests/src/com/android/systemui/complication/ComplicationHostViewControllerTest.java +38 −3 Original line number Diff line number Diff line Loading @@ -22,8 +22,12 @@ import static org.mockito.Mockito.never; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.content.res.Configuration; import android.graphics.Rect; import android.os.UserHandle; import android.provider.Settings; import android.testing.TestableLooper; import android.testing.ViewUtils; import android.view.View; import androidx.constraintlayout.widget.ConstraintLayout; Loading @@ -35,6 +39,7 @@ import androidx.test.filters.SmallTest; import com.android.systemui.SysuiTestCase; import com.android.systemui.dreams.DreamOverlayStateController; import com.android.systemui.kosmos.KosmosJavaAdapter; import com.android.systemui.util.settings.FakeSettings; import com.android.systemui.util.settings.SecureSettings; Loading @@ -52,8 +57,8 @@ import java.util.HashSet; @SmallTest @RunWith(AndroidJUnit4.class) @TestableLooper.RunWithLooper(setAsMainLooper = true) public class ComplicationHostViewControllerTest extends SysuiTestCase { @Mock ConstraintLayout mComplicationHostView; @Mock Loading Loading @@ -99,6 +104,10 @@ public class ComplicationHostViewControllerTest extends SysuiTestCase { private SecureSettings mSecureSettings; private KosmosJavaAdapter mKosmos; private TestableLooper mLooper; private static final int CURRENT_USER_ID = UserHandle.USER_SYSTEM; @Before Loading @@ -113,7 +122,10 @@ public class ComplicationHostViewControllerTest extends SysuiTestCase { when(mViewHolder.getLayoutParams()).thenReturn(mComplicationLayoutParams); when(mComplicationView.getParent()).thenReturn(mComplicationHostView); mLooper = TestableLooper.get(this); mKosmos = new KosmosJavaAdapter(this); mSecureSettings = new FakeSettings(); mComplicationHostView = new ConstraintLayout(getContext()); mSecureSettings.putFloatForUser( Settings.Global.ANIMATOR_DURATION_SCALE, 1.0f, CURRENT_USER_ID); Loading @@ -123,11 +135,34 @@ public class ComplicationHostViewControllerTest extends SysuiTestCase { mDreamOverlayStateController, mLifecycleOwner, mViewModel, mSecureSettings); mSecureSettings, mKosmos.getConfigurationInteractor(), mKosmos.getTestDispatcher() ); mController.init(); } /** * Ensures layout engine update is called on configuration change. */ @Test public void testUpdateLayoutEngineOnConfigurationChange() { mController.onViewAttached(); // Attach the complication host view so flows collecting on it start running. ViewUtils.attachView(mComplicationHostView); mLooper.processAllMessages(); // emit configuration change Rect bounds = new Rect(0, 0, 2000, 2000); Configuration config = new Configuration(); config.windowConfiguration.setMaxBounds(bounds); mKosmos.getConfigurationRepository().onConfigurationChange(config); mKosmos.getTestScope().getTestScheduler().runCurrent(); verify(mLayoutEngine).updateLayoutEngine(bounds); } /** * Ensures the lifecycle of complications is properly handled. */ Loading packages/SystemUI/multivalentTests/src/com/android/systemui/complication/ComplicationLayoutEngineTest.java +63 −24 Original line number Diff line number Diff line Loading @@ -18,10 +18,12 @@ package com.android.systemui.complication; import static com.google.common.truth.Truth.assertThat; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.never; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.graphics.Rect; import android.view.View; import androidx.constraintlayout.widget.ConstraintLayout; Loading Loading @@ -56,12 +58,14 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Mock TouchInsetManager.TouchInsetSession mTouchSession; Margins mMargins = new Margins(0, 0, 0, 0); ComplicationLayoutEngine createComplicationLayoutEngine() { return createComplicationLayoutEngine(0); } ComplicationLayoutEngine createComplicationLayoutEngine(int spacing) { return new ComplicationLayoutEngine(mLayout, spacing, 0, 0, 0, 0, mTouchSession, 0, 0); return new ComplicationLayoutEngine(mLayout, spacing, () -> mMargins, mTouchSession, 0, 0); } @Before Loading @@ -84,7 +88,7 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { ConstraintLayout layout) { this.lp = params; this.category = category; this.view = Mockito.mock(View.class); this.view = mock(View.class); this.id = sFactory.getNextId(); when(view.getId()).thenReturn(sNextId++); when(view.getParent()).thenReturn(layout); Loading Loading @@ -131,15 +135,10 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testComplicationMarginPosition() { final Random rand = new Random(); final int startMargin = rand.nextInt(); final int topMargin = rand.nextInt(); final int endMargin = rand.nextInt(); final int bottomMargin = rand.nextInt(); final int spacing = rand.nextInt(); final ComplicationLayoutEngine engine = new ComplicationLayoutEngine(mLayout, spacing, startMargin, topMargin, endMargin, bottomMargin, mTouchSession, 0, 0); mMargins = new Margins(rand.nextInt(), rand.nextInt(), rand.nextInt(), rand.nextInt()); final ComplicationLayoutEngine engine = createComplicationLayoutEngine(spacing); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -167,17 +166,67 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { addComplication(engine, secondViewInfo); // The first added view should have margins from both directions from the corner position. verifyChange(firstViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(topMargin); assertThat(lp.getMarginEnd()).isEqualTo(endMargin); assertThat(lp.topMargin).isEqualTo(mMargins.top); assertThat(lp.getMarginEnd()).isEqualTo(mMargins.end); }); // The second view should be spaced below the first view and have the side end margin. verifyChange(secondViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(spacing); assertThat(lp.getMarginEnd()).isEqualTo(endMargin); assertThat(lp.getMarginEnd()).isEqualTo(mMargins.end); }); } @Test public void testComplicationMarginsOnScreenSizeChange() { final Random rand = new Random(); final int spacing = rand.nextInt(); final ComplicationLayoutEngine engine = createComplicationLayoutEngine(spacing); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, 100, ComplicationLayoutParams.POSITION_TOP | ComplicationLayoutParams.POSITION_END, ComplicationLayoutParams.DIRECTION_DOWN, 0), Complication.CATEGORY_SYSTEM, mLayout); addComplication(engine, firstViewInfo); final ViewInfo secondViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, 100, ComplicationLayoutParams.POSITION_TOP | ComplicationLayoutParams.POSITION_END, ComplicationLayoutParams.DIRECTION_DOWN, 0), Complication.CATEGORY_STANDARD, mLayout); addComplication(engine, secondViewInfo); firstViewInfo.clearInvocations(); secondViewInfo.clearInvocations(); // Triggers an update to the layout engine with new margins. final int newTopMargin = rand.nextInt(); final int newEndMargin = rand.nextInt(); mMargins = new Margins(0, newTopMargin, newEndMargin, 0); engine.updateLayoutEngine(new Rect(0, 0, 800, 1000)); // Ensure complication view have new margins verifyChange(firstViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(newTopMargin); assertThat(lp.getMarginEnd()).isEqualTo(newEndMargin); }); verifyChange(secondViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(spacing); assertThat(lp.getMarginEnd()).isEqualTo(newEndMargin); }); } Loading Loading @@ -241,7 +290,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testDirectionLayout() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -289,7 +337,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testPositionLayout() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -376,7 +423,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { public void testDefaultMargin() { final int margin = 5; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(margin); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -452,7 +498,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { final int defaultMargin = 5; final int complicationMargin = 10; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(defaultMargin); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -518,7 +563,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { public void testWidthConstraint() { final int maxWidth = 20; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo viewStartDirection = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -566,7 +610,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { public void testHeightConstraint() { final int maxHeight = 20; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo viewUpDirection = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -613,7 +656,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testConstraintNotSetWhenNotSpecified() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo view = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -641,7 +683,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testRemoval() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -687,7 +728,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testDoubleRemoval() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -716,7 +756,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testGetViews() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo topEndView = new ViewInfo( new ComplicationLayoutParams( 100, Loading packages/SystemUI/res/values/dimens.xml +7 −3 Original line number Diff line number Diff line Loading @@ -1993,10 +1993,14 @@ </item> <!-- The padding applied to the dream overlay container --> <dimen name="dream_overlay_container_padding_start">0dp</dimen> <dimen name="dream_overlay_container_padding_end">0dp</dimen> <dimen name="dream_overlay_container_padding_start">40dp</dimen> <dimen name="dream_overlay_container_padding_end">40dp</dimen> <dimen name="dream_overlay_container_padding_top">0dp</dimen> <dimen name="dream_overlay_container_padding_bottom">0dp</dimen> <dimen name="dream_overlay_container_padding_bottom">40dp</dimen> <dimen name="dream_overlay_container_small_padding_start">32dp</dimen> <dimen name="dream_overlay_container_small_padding_end">32dp</dimen> <dimen name="dream_overlay_container_small_padding_top">0dp</dimen> <dimen name="dream_overlay_container_small_padding_bottom">32dp</dimen> <!-- The margin applied between complications --> <dimen name="dream_overlay_complication_margin">0dp</dimen> Loading packages/SystemUI/src/com/android/systemui/communal/util/WindowSizeUtils.kt 0 → 100644 +45 −0 Original line number Diff line number Diff line /* * 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.systemui.communal.util import android.content.Context import androidx.compose.ui.unit.dp import androidx.window.layout.WindowMetricsCalculator /** * [WindowSizeUtils] defines viewport breakpoints that helps create responsive mobile layout. * * @see https://developer.android.com/develop/ui/views/layout/use-window-size-classes */ object WindowSizeUtils { /** Compact screen width breakpoint. */ val COMPACT_WIDTH = 600.dp /** Medium screen width breakpoint. */ val MEDIUM_WIDTH = 840.dp /** Compact screen height breakpoint. */ val COMPACT_HEIGHT = 480.dp /** Expanded screen height breakpoint. */ val EXPANDED_HEIGHT = 900.dp /** Whether the window size is compact, which reflects most mobile sizes in portrait. */ @JvmStatic fun isCompactWindowSize(context: Context): Boolean { val metrics = WindowMetricsCalculator.getOrCreate().computeCurrentWindowMetrics(context) val width = metrics.bounds.width() return width / metrics.density < COMPACT_WIDTH.value } } Loading
packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/ResponsiveLazyHorizontalGrid.kt +6 −3 Original line number Diff line number Diff line Loading @@ -48,6 +48,9 @@ import androidx.compose.ui.unit.coerceAtMost import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.times import androidx.window.layout.WindowMetricsCalculator import com.android.systemui.communal.util.WindowSizeUtils.COMPACT_HEIGHT import com.android.systemui.communal.util.WindowSizeUtils.COMPACT_WIDTH import com.android.systemui.communal.util.WindowSizeUtils.MEDIUM_WIDTH /** * Renders a responsive [LazyHorizontalGrid] with dynamic columns and rows. Each cell will maintain Loading Loading @@ -266,14 +269,14 @@ fun calculateWindowSize(): DpSize { private fun calculateNumCellsWidth(width: Dp) = // See https://developer.android.com/develop/ui/views/layout/use-window-size-classes when { width >= 840.dp -> 3 width >= 600.dp -> 2 width >= MEDIUM_WIDTH -> 3 width >= COMPACT_WIDTH -> 2 else -> 1 } private fun calculateNumCellsHeight(height: Dp) = when { height >= 1000.dp -> 3 height >= 480.dp -> 2 height >= COMPACT_HEIGHT -> 2 else -> 1 }
packages/SystemUI/multivalentTests/src/com/android/systemui/complication/ComplicationHostViewControllerTest.java +38 −3 Original line number Diff line number Diff line Loading @@ -22,8 +22,12 @@ import static org.mockito.Mockito.never; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.content.res.Configuration; import android.graphics.Rect; import android.os.UserHandle; import android.provider.Settings; import android.testing.TestableLooper; import android.testing.ViewUtils; import android.view.View; import androidx.constraintlayout.widget.ConstraintLayout; Loading @@ -35,6 +39,7 @@ import androidx.test.filters.SmallTest; import com.android.systemui.SysuiTestCase; import com.android.systemui.dreams.DreamOverlayStateController; import com.android.systemui.kosmos.KosmosJavaAdapter; import com.android.systemui.util.settings.FakeSettings; import com.android.systemui.util.settings.SecureSettings; Loading @@ -52,8 +57,8 @@ import java.util.HashSet; @SmallTest @RunWith(AndroidJUnit4.class) @TestableLooper.RunWithLooper(setAsMainLooper = true) public class ComplicationHostViewControllerTest extends SysuiTestCase { @Mock ConstraintLayout mComplicationHostView; @Mock Loading Loading @@ -99,6 +104,10 @@ public class ComplicationHostViewControllerTest extends SysuiTestCase { private SecureSettings mSecureSettings; private KosmosJavaAdapter mKosmos; private TestableLooper mLooper; private static final int CURRENT_USER_ID = UserHandle.USER_SYSTEM; @Before Loading @@ -113,7 +122,10 @@ public class ComplicationHostViewControllerTest extends SysuiTestCase { when(mViewHolder.getLayoutParams()).thenReturn(mComplicationLayoutParams); when(mComplicationView.getParent()).thenReturn(mComplicationHostView); mLooper = TestableLooper.get(this); mKosmos = new KosmosJavaAdapter(this); mSecureSettings = new FakeSettings(); mComplicationHostView = new ConstraintLayout(getContext()); mSecureSettings.putFloatForUser( Settings.Global.ANIMATOR_DURATION_SCALE, 1.0f, CURRENT_USER_ID); Loading @@ -123,11 +135,34 @@ public class ComplicationHostViewControllerTest extends SysuiTestCase { mDreamOverlayStateController, mLifecycleOwner, mViewModel, mSecureSettings); mSecureSettings, mKosmos.getConfigurationInteractor(), mKosmos.getTestDispatcher() ); mController.init(); } /** * Ensures layout engine update is called on configuration change. */ @Test public void testUpdateLayoutEngineOnConfigurationChange() { mController.onViewAttached(); // Attach the complication host view so flows collecting on it start running. ViewUtils.attachView(mComplicationHostView); mLooper.processAllMessages(); // emit configuration change Rect bounds = new Rect(0, 0, 2000, 2000); Configuration config = new Configuration(); config.windowConfiguration.setMaxBounds(bounds); mKosmos.getConfigurationRepository().onConfigurationChange(config); mKosmos.getTestScope().getTestScheduler().runCurrent(); verify(mLayoutEngine).updateLayoutEngine(bounds); } /** * Ensures the lifecycle of complications is properly handled. */ Loading
packages/SystemUI/multivalentTests/src/com/android/systemui/complication/ComplicationLayoutEngineTest.java +63 −24 Original line number Diff line number Diff line Loading @@ -18,10 +18,12 @@ package com.android.systemui.complication; import static com.google.common.truth.Truth.assertThat; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.never; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.graphics.Rect; import android.view.View; import androidx.constraintlayout.widget.ConstraintLayout; Loading Loading @@ -56,12 +58,14 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Mock TouchInsetManager.TouchInsetSession mTouchSession; Margins mMargins = new Margins(0, 0, 0, 0); ComplicationLayoutEngine createComplicationLayoutEngine() { return createComplicationLayoutEngine(0); } ComplicationLayoutEngine createComplicationLayoutEngine(int spacing) { return new ComplicationLayoutEngine(mLayout, spacing, 0, 0, 0, 0, mTouchSession, 0, 0); return new ComplicationLayoutEngine(mLayout, spacing, () -> mMargins, mTouchSession, 0, 0); } @Before Loading @@ -84,7 +88,7 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { ConstraintLayout layout) { this.lp = params; this.category = category; this.view = Mockito.mock(View.class); this.view = mock(View.class); this.id = sFactory.getNextId(); when(view.getId()).thenReturn(sNextId++); when(view.getParent()).thenReturn(layout); Loading Loading @@ -131,15 +135,10 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testComplicationMarginPosition() { final Random rand = new Random(); final int startMargin = rand.nextInt(); final int topMargin = rand.nextInt(); final int endMargin = rand.nextInt(); final int bottomMargin = rand.nextInt(); final int spacing = rand.nextInt(); final ComplicationLayoutEngine engine = new ComplicationLayoutEngine(mLayout, spacing, startMargin, topMargin, endMargin, bottomMargin, mTouchSession, 0, 0); mMargins = new Margins(rand.nextInt(), rand.nextInt(), rand.nextInt(), rand.nextInt()); final ComplicationLayoutEngine engine = createComplicationLayoutEngine(spacing); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -167,17 +166,67 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { addComplication(engine, secondViewInfo); // The first added view should have margins from both directions from the corner position. verifyChange(firstViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(topMargin); assertThat(lp.getMarginEnd()).isEqualTo(endMargin); assertThat(lp.topMargin).isEqualTo(mMargins.top); assertThat(lp.getMarginEnd()).isEqualTo(mMargins.end); }); // The second view should be spaced below the first view and have the side end margin. verifyChange(secondViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(spacing); assertThat(lp.getMarginEnd()).isEqualTo(endMargin); assertThat(lp.getMarginEnd()).isEqualTo(mMargins.end); }); } @Test public void testComplicationMarginsOnScreenSizeChange() { final Random rand = new Random(); final int spacing = rand.nextInt(); final ComplicationLayoutEngine engine = createComplicationLayoutEngine(spacing); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, 100, ComplicationLayoutParams.POSITION_TOP | ComplicationLayoutParams.POSITION_END, ComplicationLayoutParams.DIRECTION_DOWN, 0), Complication.CATEGORY_SYSTEM, mLayout); addComplication(engine, firstViewInfo); final ViewInfo secondViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, 100, ComplicationLayoutParams.POSITION_TOP | ComplicationLayoutParams.POSITION_END, ComplicationLayoutParams.DIRECTION_DOWN, 0), Complication.CATEGORY_STANDARD, mLayout); addComplication(engine, secondViewInfo); firstViewInfo.clearInvocations(); secondViewInfo.clearInvocations(); // Triggers an update to the layout engine with new margins. final int newTopMargin = rand.nextInt(); final int newEndMargin = rand.nextInt(); mMargins = new Margins(0, newTopMargin, newEndMargin, 0); engine.updateLayoutEngine(new Rect(0, 0, 800, 1000)); // Ensure complication view have new margins verifyChange(firstViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(newTopMargin); assertThat(lp.getMarginEnd()).isEqualTo(newEndMargin); }); verifyChange(secondViewInfo, false, lp -> { assertThat(lp.topMargin).isEqualTo(spacing); assertThat(lp.getMarginEnd()).isEqualTo(newEndMargin); }); } Loading Loading @@ -241,7 +290,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testDirectionLayout() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -289,7 +337,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testPositionLayout() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -376,7 +423,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { public void testDefaultMargin() { final int margin = 5; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(margin); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -452,7 +498,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { final int defaultMargin = 5; final int complicationMargin = 10; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(defaultMargin); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -518,7 +563,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { public void testWidthConstraint() { final int maxWidth = 20; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo viewStartDirection = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -566,7 +610,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { public void testHeightConstraint() { final int maxHeight = 20; final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo viewUpDirection = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -613,7 +656,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testConstraintNotSetWhenNotSpecified() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo view = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -641,7 +683,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testRemoval() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -687,7 +728,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testDoubleRemoval() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo firstViewInfo = new ViewInfo( new ComplicationLayoutParams( 100, Loading Loading @@ -716,7 +756,6 @@ public class ComplicationLayoutEngineTest extends SysuiTestCase { @Test public void testGetViews() { final ComplicationLayoutEngine engine = createComplicationLayoutEngine(); final ViewInfo topEndView = new ViewInfo( new ComplicationLayoutParams( 100, Loading
packages/SystemUI/res/values/dimens.xml +7 −3 Original line number Diff line number Diff line Loading @@ -1993,10 +1993,14 @@ </item> <!-- The padding applied to the dream overlay container --> <dimen name="dream_overlay_container_padding_start">0dp</dimen> <dimen name="dream_overlay_container_padding_end">0dp</dimen> <dimen name="dream_overlay_container_padding_start">40dp</dimen> <dimen name="dream_overlay_container_padding_end">40dp</dimen> <dimen name="dream_overlay_container_padding_top">0dp</dimen> <dimen name="dream_overlay_container_padding_bottom">0dp</dimen> <dimen name="dream_overlay_container_padding_bottom">40dp</dimen> <dimen name="dream_overlay_container_small_padding_start">32dp</dimen> <dimen name="dream_overlay_container_small_padding_end">32dp</dimen> <dimen name="dream_overlay_container_small_padding_top">0dp</dimen> <dimen name="dream_overlay_container_small_padding_bottom">32dp</dimen> <!-- The margin applied between complications --> <dimen name="dream_overlay_complication_margin">0dp</dimen> Loading
packages/SystemUI/src/com/android/systemui/communal/util/WindowSizeUtils.kt 0 → 100644 +45 −0 Original line number Diff line number Diff line /* * 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.systemui.communal.util import android.content.Context import androidx.compose.ui.unit.dp import androidx.window.layout.WindowMetricsCalculator /** * [WindowSizeUtils] defines viewport breakpoints that helps create responsive mobile layout. * * @see https://developer.android.com/develop/ui/views/layout/use-window-size-classes */ object WindowSizeUtils { /** Compact screen width breakpoint. */ val COMPACT_WIDTH = 600.dp /** Medium screen width breakpoint. */ val MEDIUM_WIDTH = 840.dp /** Compact screen height breakpoint. */ val COMPACT_HEIGHT = 480.dp /** Expanded screen height breakpoint. */ val EXPANDED_HEIGHT = 900.dp /** Whether the window size is compact, which reflects most mobile sizes in portrait. */ @JvmStatic fun isCompactWindowSize(context: Context): Boolean { val metrics = WindowMetricsCalculator.getOrCreate().computeCurrentWindowMetrics(context) val width = metrics.bounds.width() return width / metrics.density < COMPACT_WIDTH.value } }