diff --git a/quickstep/src/com/android/quickstep/QuickstepTestInformationHandler.java b/quickstep/src/com/android/quickstep/QuickstepTestInformationHandler.java index 1b8dc14154..65c8662f20 100644 --- a/quickstep/src/com/android/quickstep/QuickstepTestInformationHandler.java +++ b/quickstep/src/com/android/quickstep/QuickstepTestInformationHandler.java @@ -1,5 +1,6 @@ package com.android.quickstep; +import static com.android.launcher3.taskbar.TaskbarThresholdUtils.getFromNavThreshold; import static com.android.launcher3.util.Executors.MAIN_EXECUTOR; import android.app.Activity; @@ -10,7 +11,6 @@ import android.os.Bundle; import androidx.annotation.Nullable; -import com.android.launcher3.R; import com.android.launcher3.taskbar.TaskbarActivityContext; import com.android.launcher3.testing.TestInformationHandler; import com.android.launcher3.testing.shared.TestProtocol; @@ -99,7 +99,7 @@ public class QuickstepTestInformationHandler extends TestInformationHandler { case TestProtocol.REQUEST_TASKBAR_FROM_NAV_THRESHOLD: { final Resources resources = mContext.getResources(); response.putInt(TestProtocol.TEST_INFO_RESPONSE_FIELD, - resources.getDimensionPixelSize(R.dimen.taskbar_from_nav_threshold)); + getFromNavThreshold(resources, mDeviceProfile)); return response; } diff --git a/quickstep/tests/src/com/android/quickstep/TaplTestsTransientTaskbar.java b/quickstep/tests/src/com/android/quickstep/TaplTestsTransientTaskbar.java index 7109bbff54..38d6046828 100644 --- a/quickstep/tests/src/com/android/quickstep/TaplTestsTransientTaskbar.java +++ b/quickstep/tests/src/com/android/quickstep/TaplTestsTransientTaskbar.java @@ -25,6 +25,7 @@ import androidx.test.filters.LargeTest; import androidx.test.runner.AndroidJUnit4; import com.android.launcher3.ui.PortraitLandscapeRunner.PortraitLandscape; +import com.android.launcher3.util.rule.ScreenRecordRule.ScreenRecord; import com.android.quickstep.TaskbarModeSwitchRule.TaskbarModeSwitch; import org.junit.Test; @@ -69,6 +70,7 @@ public class TaplTestsTransientTaskbar extends AbstractTaplTestsTaskbar { @Test @TaskbarModeSwitch(mode = TRANSIENT) @PortraitLandscape + @ScreenRecord // b/317798731 public void testSwipeToStashAndUnstash() { getTaskbar().swipeDownToStash(); mLauncher.getLaunchedAppState().swipeUpToUnstashTaskbar(); diff --git a/src/com/android/launcher3/allapps/AlphabeticalAppsList.java b/src/com/android/launcher3/allapps/AlphabeticalAppsList.java index 17827918b8..3e55f610a1 100644 --- a/src/com/android/launcher3/allapps/AlphabeticalAppsList.java +++ b/src/com/android/launcher3/allapps/AlphabeticalAppsList.java @@ -22,6 +22,7 @@ import static com.android.launcher3.allapps.SectionDecorationInfo.ROUND_NOTHING; import android.content.Context; import androidx.annotation.Nullable; +import androidx.annotation.VisibleForTesting; import androidx.recyclerview.widget.DiffUtil; import com.android.launcher3.Flags; @@ -338,26 +339,14 @@ public class AlphabeticalAppsList implement hasPrivateApps = appList.stream(). allMatch(mPrivateProviderManager.getItemInfoMatcher()); } - int privateAppCount = 0; - int numberOfColumns = mActivityContext.getDeviceProfile().numShownAllAppsColumns; - int numberOfAppRows = (int) Math.ceil((double) appList.size() / numberOfColumns); - for (AppInfo info : appList) { + for (int i = 0; i < appList.size(); i++) { + AppInfo info = appList.get(i); // Apply decorator to private apps. if (hasPrivateApps) { - int roundRegion = ROUND_NOTHING; - if ((privateAppCount / numberOfColumns) == numberOfAppRows - 1) { - if ((privateAppCount % numberOfColumns) == 0) { - // App is the first column - roundRegion = ROUND_BOTTOM_LEFT; - } else if ((privateAppCount % numberOfColumns) == numberOfColumns-1) { - roundRegion = ROUND_BOTTOM_RIGHT; - } - } mAdapterItems.add(AdapterItem.asAppWithDecorationInfo(info, new SectionDecorationInfo(mActivityContext.getApplicationContext(), - roundRegion, + getRoundRegions(i, appList.size()), true /* decorateTogether */))); - privateAppCount += 1; } else { mAdapterItems.add(AdapterItem.asApp(info)); } @@ -372,6 +361,43 @@ public class AlphabeticalAppsList implement } } + /** + * Determines the corner regions that should be rounded for a specific app icon based on its + * position in a grid. Apps that should only be cared about rounding are the apps in the last + * row. In the last row on the first column, the app should only be rounded on the bottom left. + * Apps in the middle would not be rounded and the last app on the last row will ALWAYS have a + * {@link SectionDecorationInfo#ROUND_BOTTOM_RIGHT}. + * + * @param appIndex The index of the app icon within the app list. + * @param appListSize The total number of apps within the app list. + * @return An integer representing the corner regions to be rounded, using bitwise flags: + * - {@link SectionDecorationInfo#ROUND_NOTHING}: No corners should be rounded. + * - {@link SectionDecorationInfo#ROUND_TOP_LEFT}: Round the top-left corner. + * - {@link SectionDecorationInfo#ROUND_TOP_RIGHT}: Round the top-right corner. + * - {@link SectionDecorationInfo#ROUND_BOTTOM_LEFT}: Round the bottom-left corner. + * - {@link SectionDecorationInfo#ROUND_BOTTOM_RIGHT}: Round the bottom-right corner. + */ + @VisibleForTesting + int getRoundRegions(int appIndex, int appListSize) { + int numberOfAppRows = (int) Math.ceil((double) appListSize / mNumAppsPerRowAllApps); + int roundRegion = ROUND_NOTHING; + // App is in the last row. + if ((appIndex / mNumAppsPerRowAllApps) == numberOfAppRows - 1) { + if ((appIndex % mNumAppsPerRowAllApps) == 0) { + // App is the first column. + roundRegion = ROUND_BOTTOM_LEFT; + } else if ((appIndex % mNumAppsPerRowAllApps) == mNumAppsPerRowAllApps-1) { + // App is in the last column. + roundRegion = ROUND_BOTTOM_RIGHT; + } + // Ensure the last private app is rounded on the bottom right. + if (appIndex == appListSize - 1) { + roundRegion |= ROUND_BOTTOM_RIGHT; + } + } + return roundRegion; + } + private static class MyDiffCallback extends DiffUtil.Callback { private final List mOldList; diff --git a/src/com/android/launcher3/allapps/SectionDecorationInfo.java b/src/com/android/launcher3/allapps/SectionDecorationInfo.java index 1fed2b654e..c438d19b3e 100644 --- a/src/com/android/launcher3/allapps/SectionDecorationInfo.java +++ b/src/com/android/launcher3/allapps/SectionDecorationInfo.java @@ -22,11 +22,11 @@ import androidx.annotation.NonNull; public class SectionDecorationInfo { - public static final int ROUND_NOTHING = 1 << 1; - public static final int ROUND_TOP_LEFT = 1 << 2; - public static final int ROUND_TOP_RIGHT = 1 << 3; - public static final int ROUND_BOTTOM_LEFT = 1 << 4; - public static final int ROUND_BOTTOM_RIGHT = 1 << 5; + public static final int ROUND_NOTHING = 0; + public static final int ROUND_TOP_LEFT = 1 << 1; + public static final int ROUND_TOP_RIGHT = 1 << 2; + public static final int ROUND_BOTTOM_LEFT = 1 << 3; + public static final int ROUND_BOTTOM_RIGHT = 1 << 4; public static final int DECORATOR_ALPHA = 255; protected boolean mShouldDecorateItemsTogether; diff --git a/tests/src/com/android/launcher3/allapps/AlphabeticalAppsListTest.java b/tests/src/com/android/launcher3/allapps/AlphabeticalAppsListTest.java index 259f5199db..306878531c 100644 --- a/tests/src/com/android/launcher3/allapps/AlphabeticalAppsListTest.java +++ b/tests/src/com/android/launcher3/allapps/AlphabeticalAppsListTest.java @@ -19,6 +19,9 @@ package com.android.launcher3.allapps; import static androidx.test.core.app.ApplicationProvider.getApplicationContext; import static com.android.launcher3.allapps.BaseAllAppsAdapter.VIEW_TYPE_PRIVATE_SPACE_HEADER; +import static com.android.launcher3.allapps.SectionDecorationInfo.ROUND_BOTTOM_LEFT; +import static com.android.launcher3.allapps.SectionDecorationInfo.ROUND_BOTTOM_RIGHT; +import static com.android.launcher3.allapps.SectionDecorationInfo.ROUND_NOTHING; import static com.android.launcher3.allapps.UserProfileManager.STATE_DISABLED; import static com.android.launcher3.allapps.UserProfileManager.STATE_ENABLED; import static com.android.launcher3.allapps.UserProfileManager.STATE_TRANSITION; @@ -61,6 +64,8 @@ public class AlphabeticalAppsListTest { private static final int PRIVATE_SPACE_HEADER_ITEM_COUNT = 1; private static final int MAIN_USER_APP_COUNT = 2; private static final int PRIVATE_USER_APP_COUNT = 1; + private static final int NUM_APP_COLS = 4; + private static final int NUM_APP_ROWS = 3; private AlphabeticalAppsList mAlphabeticalAppsList; @Mock @@ -81,6 +86,7 @@ public class AlphabeticalAppsListTest { info != null && info.user.equals(PRIVATE_HANDLE)); mAlphabeticalAppsList = new AlphabeticalAppsList<>(mContext, mAllAppsStore, null, mPrivateProfileManager); + mAlphabeticalAppsList.setNumAppsPerRowAllApps(NUM_APP_COLS); } @Test @@ -182,6 +188,94 @@ public class AlphabeticalAppsListTest { .toList().size()); } + @Test + public void getRoundRegions_whenIndexIsMiddleOfLastRow_roundNothing() { + int index = 3; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, + NUM_APP_COLS * NUM_APP_ROWS); + + assertEquals(ROUND_NOTHING, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInEndOfLastRow_roundBottomRight() { + int index = 11; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, + NUM_APP_COLS * NUM_APP_ROWS); + + assertEquals(ROUND_BOTTOM_RIGHT, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInBeginningOfLastRow_roundBottomLeft() { + int index = 8; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, + NUM_APP_COLS * NUM_APP_ROWS); + + assertEquals(ROUND_BOTTOM_LEFT, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInMiddleOfLastRow_roundNothing() { + int index = 9; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, + NUM_APP_COLS * NUM_APP_ROWS); + + assertEquals(ROUND_NOTHING, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInMiddleRow_roundNothing() { + int index = 5; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, + NUM_APP_COLS * NUM_APP_ROWS); + + assertEquals(ROUND_NOTHING, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInBeginningOfTopRow_roundNothing() { + int index = 0; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, + NUM_APP_COLS * NUM_APP_ROWS); + + assertEquals(ROUND_NOTHING, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInLastOfTopRow_roundNothing() { + int index = 3; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, + NUM_APP_COLS * NUM_APP_ROWS); + + assertEquals(ROUND_NOTHING, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInMiddleOfLastRowLastItem_roundBottomRight() { + int index = 9; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, index+1); + + assertEquals(ROUND_BOTTOM_RIGHT, roundRegions); + } + + @Test + public void getRoundRegions_whenIndexIsInBeginningOfLastRowLastItem_roundBottomRight() { + int index = 8; + + int roundRegions = mAlphabeticalAppsList.getRoundRegions(index, index+1); + + assertEquals(ROUND_BOTTOM_RIGHT | ROUND_BOTTOM_LEFT, roundRegions); + } + private int addPrivateSpaceHeader(List adapterItemList) { adapterItemList.add(new BaseAllAppsAdapter.AdapterItem(VIEW_TYPE_PRIVATE_SPACE_HEADER)); return adapterItemList.size();