From 839fb7b3aedee54065e3cba307c878df25cb3343 Mon Sep 17 00:00:00 2001 From: vadimt Date: Mon, 22 Jun 2020 15:01:49 -0700 Subject: [PATCH 01/12] Eliminating messages that launcher activity is frozen They were ultimately caused by killing Launcher process from tests. Now having a test info handler request to clear db. Bug: 152629799 Change-Id: Ia81ddc3e338718c4cff08c7396b9fda1b7091024 --- .../testing/DebugTestInformationHandler.java | 13 +++++++++++++ .../android/launcher3/testing/TestProtocol.java | 1 + .../launcher3/ui/AbstractLauncherUiTest.java | 14 +++----------- .../launcher3/tapl/LauncherInstrumentation.java | 4 ++++ 4 files changed, 21 insertions(+), 11 deletions(-) diff --git a/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java b/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java index ad21106759..0b7d4bf27e 100644 --- a/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java +++ b/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java @@ -18,6 +18,8 @@ package com.android.launcher3.testing; import static android.graphics.Bitmap.Config.ARGB_8888; +import static com.android.launcher3.util.Executors.MAIN_EXECUTOR; + import android.content.Context; import android.graphics.Bitmap; import android.graphics.Color; @@ -28,6 +30,9 @@ import android.view.View; import androidx.annotation.Keep; +import com.android.launcher3.LauncherAppState; +import com.android.launcher3.LauncherSettings; + import java.util.ArrayList; import java.util.Collection; import java.util.LinkedList; @@ -165,6 +170,14 @@ public class DebugTestInformationHandler extends TestInformationHandler { return response; } + case TestProtocol.REQUEST_CLEAR_DATA: { + LauncherSettings.Settings.call(mContext.getContentResolver(), + LauncherSettings.Settings.METHOD_CREATE_EMPTY_DB); + MAIN_EXECUTOR.submit(() -> + LauncherAppState.getInstance(mContext).getModel().forceReload()); + return response; + } + default: return super.call(method); } diff --git a/src/com/android/launcher3/testing/TestProtocol.java b/src/com/android/launcher3/testing/TestProtocol.java index 49da7b3d8d..3ca08fd8ec 100644 --- a/src/com/android/launcher3/testing/TestProtocol.java +++ b/src/com/android/launcher3/testing/TestProtocol.java @@ -91,6 +91,7 @@ public final class TestProtocol { public static final String REQUEST_START_EVENT_LOGGING = "start-event-logging"; public static final String REQUEST_GET_TEST_EVENTS = "get-test-events"; public static final String REQUEST_STOP_EVENT_LOGGING = "stop-event-logging"; + public static final String REQUEST_CLEAR_DATA = "clear-data"; public static boolean sDebugTracing = false; public static final String REQUEST_ENABLE_DEBUG_TRACING = "enable-debug-tracing"; diff --git a/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java b/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java index 3d39d254b1..858e183ab7 100644 --- a/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java +++ b/tests/src/com/android/launcher3/ui/AbstractLauncherUiTest.java @@ -300,17 +300,9 @@ public abstract class AbstractLauncherUiTest { checkDetectedLeaks(mLauncher); } - protected void clearLauncherData() throws IOException, InterruptedException { - if (TestHelpers.isInLauncherProcess()) { - LauncherSettings.Settings.call(mTargetContext.getContentResolver(), - LauncherSettings.Settings.METHOD_CREATE_EMPTY_DB); - resetLoaderState(); - } else { - clearPackageData(mDevice.getLauncherPackageName()); - mLauncher.enableDebugTracing(); - mLauncherPid = mLauncher.getPid(); - mLauncher.waitForLauncherInitialized(); - } + protected void clearLauncherData() { + mLauncher.clearLauncherData(); + mLauncher.waitForLauncherInitialized(); } /** diff --git a/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java b/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java index f634ce1951..5cf5d0fa88 100644 --- a/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java +++ b/tests/tapl/com/android/launcher3/tapl/LauncherInstrumentation.java @@ -1335,6 +1335,10 @@ public final class LauncherInstrumentation { return tasks; } + public void clearLauncherData() { + getTestInfo(TestProtocol.REQUEST_CLEAR_DATA); + } + public Closable eventsCheck() { Assert.assertTrue("Nested event checking", mEventChecker == null); disableSensorRotation(); From efb7e60edcbe7de90bf1ff2515b2016d4603de64 Mon Sep 17 00:00:00 2001 From: Tony Wickham Date: Mon, 22 Jun 2020 17:37:07 -0700 Subject: [PATCH 02/12] Store newGestureState before onConsumerAboutToBeSwitched clears it Bug: 159659393 Change-Id: If98d54b7ca397ef56a5c6d50c0fd92f25a9494b4 --- .../src/com/android/quickstep/TouchInteractionService.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java index 7d70155781..aed444d4b6 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/TouchInteractionService.java @@ -480,8 +480,9 @@ public class TouchInteractionService extends Service implements PluginListener Date: Mon, 22 Jun 2020 16:30:58 -0700 Subject: [PATCH 03/12] Log query_length & parent_container for actions on search results. Bug: 154717227 Change-Id: I8e7d725014f60a2fd9a7fe13fce705acbc7623ad --- protos/launcher_atom.proto | 9 ++++ .../logging/StatsLogCompatManager.java | 50 +++++++++++++------ .../launcher3/model/data/ItemInfo.java | 2 +- 3 files changed, 44 insertions(+), 17 deletions(-) diff --git a/protos/launcher_atom.proto b/protos/launcher_atom.proto index 98ce9af2d6..561196941c 100644 --- a/protos/launcher_atom.proto +++ b/protos/launcher_atom.proto @@ -71,6 +71,15 @@ message PredictionContainer { // Represents the apps container within search results. message SearchResultContainer { + + // Length of search term. + optional int32 query_length = 1; + + // Container from where search was invoked. + oneof ParentContainer { + WorkspaceContainer workspace = 2; + AllAppsContainer all_apps_container = 3; + } } // Container for package specific shortcuts to deep links and notifications. diff --git a/quickstep/src/com/android/quickstep/logging/StatsLogCompatManager.java b/quickstep/src/com/android/quickstep/logging/StatsLogCompatManager.java index 20348017fe..eac45e9907 100644 --- a/quickstep/src/com/android/quickstep/logging/StatsLogCompatManager.java +++ b/quickstep/src/com/android/quickstep/logging/StatsLogCompatManager.java @@ -17,7 +17,7 @@ package com.android.quickstep.logging; import static com.android.launcher3.logger.LauncherAtom.ContainerInfo.ContainerCase.FOLDER; -import static com.android.launcher3.logger.LauncherAtom.ContainerInfo.ContainerCase.PREDICTED_HOTSEAT_CONTAINER; +import static com.android.launcher3.logger.LauncherAtom.ContainerInfo.ContainerCase.SEARCH_RESULT_CONTAINER; import static com.android.launcher3.logging.StatsLogManager.LauncherEvent.LAUNCHER_WORKSPACE_SNAPSHOT; import static com.android.systemui.shared.system.SysUiStatsLog.LAUNCHER_UICHANGED__DST_STATE__ALLAPPS; import static com.android.systemui.shared.system.SysUiStatsLog.LAUNCHER_UICHANGED__DST_STATE__BACKGROUND; @@ -75,6 +75,7 @@ public class StatsLogCompatManager extends StatsLogManager { // from nano to lite, bake constant to prevent robo test failure. private static final int DEFAULT_PAGE_INDEX = -2; private static final int FOLDER_HIERARCHY_OFFSET = 100; + private static final int SEARCH_RESULT_HIERARCHY_OFFSET = 200; public StatsLogCompatManager(Context context) { sContext = context; @@ -156,10 +157,10 @@ public class StatsLogCompatManager extends StatsLogManager { getComponentName(info) /* component_name */, getGridX(info, false) /* grid_x */, getGridY(info, false) /* grid_y */, - getPageId(info, false) /* page_id */, + getPageId(info) /* page_id */, getGridX(info, true) /* grid_x_parent */, getGridY(info, true) /* grid_y_parent */, - getPageId(info, true) /* page_id_parent */, + getParentPageId(info) /* page_id_parent */, getHierarchy(info) /* hierarchy */, info.getIsWork() /* is_work_profile */, info.getAttribute().getNumber() /* origin */, @@ -321,10 +322,10 @@ public class StatsLogCompatManager extends StatsLogManager { getComponentName(atomInfo) /* component_name */, getGridX(atomInfo, false) /* grid_x */, getGridY(atomInfo, false) /* grid_y */, - getPageId(atomInfo, false) /* page_id */, + getPageId(atomInfo) /* page_id */, getGridX(atomInfo, true) /* grid_x_parent */, getGridY(atomInfo, true) /* grid_y_parent */, - getPageId(atomInfo, true) /* page_id_parent */, + getParentPageId(atomInfo) /* page_id_parent */, getHierarchy(atomInfo) /* hierarchy */, atomInfo.getIsWork() /* is_work_profile */, atomInfo.getRank() /* rank */, @@ -336,9 +337,14 @@ public class StatsLogCompatManager extends StatsLogManager { } private static int getCardinality(LauncherAtom.ItemInfo info) { - return info.getContainerInfo().getContainerCase().equals(PREDICTED_HOTSEAT_CONTAINER) - ? info.getContainerInfo().getPredictedHotseatContainer().getCardinality() - : info.getFolderIcon().getCardinality(); + switch (info.getContainerInfo().getContainerCase()){ + case PREDICTED_HOTSEAT_CONTAINER: + return info.getContainerInfo().getPredictedHotseatContainer().getCardinality(); + case SEARCH_RESULT_CONTAINER: + return info.getContainerInfo().getSearchResultContainer().getQueryLength(); + default: + return info.getFolderIcon().getCardinality(); + } } private static String getPackageName(LauncherAtom.ItemInfo info) { @@ -395,15 +401,24 @@ public class StatsLogCompatManager extends StatsLogManager { } } - private static int getPageId(LauncherAtom.ItemInfo info, boolean parent) { - if (info.getContainerInfo().getContainerCase() == FOLDER) { - if (parent) { - return info.getContainerInfo().getFolder().getWorkspace().getPageIndex(); - } else { + private static int getPageId(LauncherAtom.ItemInfo info) { + switch (info.getContainerInfo().getContainerCase()) { + case FOLDER: return info.getContainerInfo().getFolder().getPageIndex(); - } - } else { - return info.getContainerInfo().getWorkspace().getPageIndex(); + default: + return info.getContainerInfo().getWorkspace().getPageIndex(); + } + } + + private static int getParentPageId(LauncherAtom.ItemInfo info) { + switch (info.getContainerInfo().getContainerCase()) { + case FOLDER: + return info.getContainerInfo().getFolder().getWorkspace().getPageIndex(); + case SEARCH_RESULT_CONTAINER: + return info.getContainerInfo().getSearchResultContainer().getWorkspace() + .getPageIndex(); + default: + return info.getContainerInfo().getWorkspace().getPageIndex(); } } @@ -411,6 +426,9 @@ public class StatsLogCompatManager extends StatsLogManager { if (info.getContainerInfo().getContainerCase() == FOLDER) { return info.getContainerInfo().getFolder().getParentContainerCase().getNumber() + FOLDER_HIERARCHY_OFFSET; + } else if (info.getContainerInfo().getContainerCase() == SEARCH_RESULT_CONTAINER) { + return info.getContainerInfo().getSearchResultContainer().getParentContainerCase() + .getNumber() + SEARCH_RESULT_HIERARCHY_OFFSET; } else { return info.getContainerInfo().getContainerCase().getNumber(); } diff --git a/src/com/android/launcher3/model/data/ItemInfo.java b/src/com/android/launcher3/model/data/ItemInfo.java index 3082b6e341..0d3ddad183 100644 --- a/src/com/android/launcher3/model/data/ItemInfo.java +++ b/src/com/android/launcher3/model/data/ItemInfo.java @@ -344,7 +344,7 @@ public class ItemInfo { return itemBuilder; } - ContainerInfo getContainerInfo() { + protected ContainerInfo getContainerInfo() { switch (container) { case CONTAINER_HOTSEAT: return ContainerInfo.newBuilder() From 76773cd210ce52edfaa5c37b72fef188279ad265 Mon Sep 17 00:00:00 2001 From: Tracy Zhou Date: Mon, 22 Jun 2020 15:30:22 -0700 Subject: [PATCH 04/12] Support having dup items in folder for migration Fixes: 159312066 Test: Have two dup items in a folder under one grid setting. Migrate. Make sure the folder is migrated correctly to the new grid setting. Change-Id: Ic5aeb30a1c8acb382bccf744d7553913d8a8a320 --- .../model/GridSizeMigrationTaskV2.java | 31 ++++++++++++------- 1 file changed, 20 insertions(+), 11 deletions(-) diff --git a/src/com/android/launcher3/model/GridSizeMigrationTaskV2.java b/src/com/android/launcher3/model/GridSizeMigrationTaskV2.java index 25a2c695f1..ebdfa8c820 100644 --- a/src/com/android/launcher3/model/GridSizeMigrationTaskV2.java +++ b/src/com/android/launcher3/model/GridSizeMigrationTaskV2.java @@ -248,10 +248,10 @@ public class GridSizeMigrationTaskV2 { /** Return what's in the src but not in the dest */ private static List calcDiff(List src, List dest) { Set destIntentSet = new HashSet<>(); - Set> destFolderIntentSet = new HashSet<>(); + Set> destFolderIntentSet = new HashSet<>(); for (DbEntry entry : dest) { if (entry.itemType == LauncherSettings.Favorites.ITEM_TYPE_FOLDER) { - destFolderIntentSet.add(entry.mFolderItems.keySet()); + destFolderIntentSet.add(getFolderIntents(entry)); } else { destIntentSet.add(entry.mIntent); } @@ -259,7 +259,7 @@ public class GridSizeMigrationTaskV2 { List diff = new ArrayList<>(); for (DbEntry entry : src) { if (entry.itemType == LauncherSettings.Favorites.ITEM_TYPE_FOLDER) { - if (!destFolderIntentSet.contains(entry.mFolderItems.keySet())) { + if (!destFolderIntentSet.contains(getFolderIntents(entry))) { diff.add(entry); } } else { @@ -271,13 +271,23 @@ public class GridSizeMigrationTaskV2 { return diff; } + private static Map getFolderIntents(DbEntry entry) { + Map folder = new HashMap<>(); + for (String intent : entry.mFolderItems.keySet()) { + folder.put(intent, entry.mFolderItems.get(intent).size()); + } + return folder; + } + private static void insertEntryInDb(SQLiteDatabase db, Context context, DbEntry entry, String srcTableName, String destTableName) { int id = copyEntryAndUpdate(db, context, entry, srcTableName, destTableName); if (entry.itemType == LauncherSettings.Favorites.ITEM_TYPE_FOLDER) { - for (int itemId : entry.mFolderItems.values()) { - copyEntryAndUpdate(db, context, itemId, id, srcTableName, destTableName); + for (Set itemIds : entry.mFolderItems.values()) { + for (int itemId : itemIds) { + copyEntryAndUpdate(db, context, itemId, id, srcTableName, destTableName); + } } } } @@ -675,7 +685,10 @@ public class GridSizeMigrationTaskV2 { String intent = c.getString(1); verifyIntent(intent); total++; - entry.mFolderItems.put(intent, id); + if (!entry.mFolderItems.containsKey(intent)) { + entry.mFolderItems.put(intent, new HashSet<>()); + } + entry.mFolderItems.get(intent).add(id); } catch (Exception e) { removeEntryFromDb(mDb, mTableName, IntArray.wrap(c.getInt(0))); } @@ -714,7 +727,7 @@ public class GridSizeMigrationTaskV2 { private String mIntent; private String mProvider; - private Map mFolderItems = new HashMap<>(); + private Map> mFolderItems = new HashMap<>(); /** Comparator according to the reading order */ @Override @@ -748,9 +761,5 @@ public class GridSizeMigrationTaskV2 { values.put(LauncherSettings.Favorites.SPANX, spanX); values.put(LauncherSettings.Favorites.SPANY, spanY); } - - public String getIntentStr() { - return mIntent; - } } } From 8108009929a51800659826b98e1257f1d8bea583 Mon Sep 17 00:00:00 2001 From: Riddle Hsu Date: Tue, 23 Jun 2020 16:52:04 +0800 Subject: [PATCH 05/12] Use isolated display context to get display info While display is in landscape, and the launcher is transformed to portrait, the display rotation from activity or application context will get the rotation in portrait. In order to transform the input event when the orientations are different, the actual device rotation is still needed. By creating the display context from application context, the resources of the new context won't be affected by the activity/application level display info adjustments. That provides the actual device states. Additionally, DefaultDisplay#INSTANCE should only be used for the operations related to physical orientation/size because it won't contain the override information from activity. Bug: 157456493 Test: Use a device which may switch refresh rate. Open Maps and put device in landscape. Use gesture navigation to swipe up. The direction of movement should be consistent with UI. Change-Id: I03108b1ab057e28727b6a6db3629d2c1c069e828 --- .../launcher3/util/DefaultDisplay.java | 20 +++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/src/com/android/launcher3/util/DefaultDisplay.java b/src/com/android/launcher3/util/DefaultDisplay.java index 150fb5b043..35788a54c8 100644 --- a/src/com/android/launcher3/util/DefaultDisplay.java +++ b/src/com/android/launcher3/util/DefaultDisplay.java @@ -49,20 +49,25 @@ public class DefaultDisplay implements DisplayListener { public static final int CHANGE_ALL = CHANGE_SIZE | CHANGE_ROTATION | CHANGE_FRAME_DELAY; - private final Context mContext; + private final Context mDisplayContext; private final int mId; private final ArrayList mListeners = new ArrayList<>(); private final Handler mChangeHandler; private Info mInfo; private DefaultDisplay(Context context) { - mContext = context; - mInfo = new Info(context); + DisplayManager dm = context.getSystemService(DisplayManager.class); + // Use application context to create display context so that it can have its own Resources. + mDisplayContext = context.getApplicationContext().createDisplayContext( + dm.getDisplay(DEFAULT_DISPLAY)); + // Note that the Display object must be obtained from DisplayManager which is associated to + // the display context, so the Display is isolated from Activity and Application to provide + // the actual state of device that excludes the additional adjustment and override. + mInfo = new Info(mDisplayContext); mId = mInfo.id; mChangeHandler = new Handler(this::onChange); - context.getSystemService(DisplayManager.class) - .registerDisplayListener(this, UI_HELPER_EXECUTOR.getHandler()); + dm.registerDisplayListener(this, UI_HELPER_EXECUTOR.getHandler()); } @Override @@ -78,7 +83,7 @@ public class DefaultDisplay implements DisplayListener { } Info oldInfo = mInfo; - Info info = new Info(mContext); + Info info = new Info(mDisplayContext); int change = 0; if (info.hasDifferentSize(oldInfo)) { @@ -162,8 +167,7 @@ public class DefaultDisplay implements DisplayListener { display.getRealSize(realSize); display.getCurrentSizeRange(smallestSize, largestSize); - Context defaultDisplayContext = context.createDisplayContext(display); - metrics = defaultDisplayContext.getResources().getDisplayMetrics(); + metrics = context.getResources().getDisplayMetrics(); } private boolean hasDifferentSize(Info info) { From a44c09d6c9fb58280a8d95c6ff3a59b630fed0f4 Mon Sep 17 00:00:00 2001 From: Samuel Fufa Date: Tue, 23 Jun 2020 12:46:30 -0700 Subject: [PATCH 06/12] Fix hotseat button alignment Screenshot: https://screenshot.googleplex.com/Vr9FXe3oN2t Bug: 159731214 Change-Id: I9e413f5d9bf0144edd413cc5995e7f1fda152f28 --- .../recents_ui_overrides/res/layout/predicted_hotseat_edu.xml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/quickstep/recents_ui_overrides/res/layout/predicted_hotseat_edu.xml b/quickstep/recents_ui_overrides/res/layout/predicted_hotseat_edu.xml index 36c9b00e07..1dab48267b 100644 --- a/quickstep/recents_ui_overrides/res/layout/predicted_hotseat_edu.xml +++ b/quickstep/recents_ui_overrides/res/layout/predicted_hotseat_edu.xml @@ -90,6 +90,7 @@ android:layout_height="wrap_content" android:background="?android:attr/selectableItemBackground" android:text="@string/hotseat_edu_dismiss" + android:layout_gravity="start|center_vertical" android:textColor="@android:color/white"/> From efa3acddba1845fa79570f900118542cf632e43a Mon Sep 17 00:00:00 2001 From: vadimt Date: Tue, 23 Jun 2020 13:59:11 -0700 Subject: [PATCH 07/12] Making LauncherProvider think that clear-db request comes from Launcher If it comes from the test process, the request won't be honored. Bug: 159728364 Change-Id: I90029c1198634f1f1e94f61ba8ab9b41609d9ad5 --- .../testing/DebugTestInformationHandler.java | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java b/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java index 0b7d4bf27e..e649ce1de4 100644 --- a/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java +++ b/ext_tests/src/com/android/launcher3/testing/DebugTestInformationHandler.java @@ -23,6 +23,7 @@ import static com.android.launcher3.util.Executors.MAIN_EXECUTOR; import android.content.Context; import android.graphics.Bitmap; import android.graphics.Color; +import android.os.Binder; import android.os.Bundle; import android.os.Debug; import android.system.Os; @@ -171,11 +172,16 @@ public class DebugTestInformationHandler extends TestInformationHandler { } case TestProtocol.REQUEST_CLEAR_DATA: { - LauncherSettings.Settings.call(mContext.getContentResolver(), - LauncherSettings.Settings.METHOD_CREATE_EMPTY_DB); - MAIN_EXECUTOR.submit(() -> - LauncherAppState.getInstance(mContext).getModel().forceReload()); - return response; + final long identity = Binder.clearCallingIdentity(); + try { + LauncherSettings.Settings.call(mContext.getContentResolver(), + LauncherSettings.Settings.METHOD_CREATE_EMPTY_DB); + MAIN_EXECUTOR.submit(() -> + LauncherAppState.getInstance(mContext).getModel().forceReload()); + return response; + } finally { + Binder.restoreCallingIdentity(identity); + } } default: From f2daafcdf8b2ef54ca4f8654b124c5cc4a644782 Mon Sep 17 00:00:00 2001 From: Vinit Nayak Date: Fri, 19 Jun 2020 19:10:31 -0700 Subject: [PATCH 08/12] Prevent premature resetting of quickswitch mode Previously, whenever a user returned to the same rotation that they had started quickswitch in, we were sending sysui the reset flag(-1) indicating that quickstep was complete instead of sending the rotation of the device the user was in. This was intentional and it worked, however we now always send the active rotation while the user is in a quickswitch session because sysui needs to show the fake home handle for immersive apps, which can occur in any rotation. This state is distinct from not being in quickswitch at all, in which no fake handles are shown. Fixes: 158677967 Change-Id: I910324abf781b4b30fe981139712bcb5b653c318 --- .../OrientationTouchTransformer.java | 35 ++++++++---- .../RecentsAnimationDeviceState.java | 57 +++++++++---------- 2 files changed, 53 insertions(+), 39 deletions(-) diff --git a/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java b/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java index 3375c53124..cf5659c7d4 100644 --- a/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java +++ b/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java @@ -68,13 +68,13 @@ class OrientationTouchTransformer { private Resources mResources; private OrientationRectF mLastRectTouched; /** - * The rotation of the last touched nav bar. Derived from {@link #mLastRectTouched}, but has a - * longer lifetime than the rect. Note this is different than {@link #mQuickStepStartingRotation} - * as it always updates its value on every touch whereas mQuickstepStartingRotation only - * updates when device rotation matches touch rotation. Maybe this will be only one necessary - * after TODO(b/154580671) is in. TBD. + * The rotation of the last touched nav bar, whether that be through the last region the user + * touched down on or valid rotation user turned their device to. + * Note this is different than + * {@link #mQuickStepStartingRotation} as it always updates its value on every touch whereas + * mQuickstepStartingRotation only updates when device rotation matches touch rotation. */ - private int mLastRectRotation; + private int mActiveTouchRotation; private SysUINavigationMode.Mode mMode; private QuickStepContractInfo mContractInfo; @@ -159,12 +159,26 @@ class OrientationTouchTransformer { if (mEnableMultipleRegions) { mQuickStepStartingRotation = info.rotation; } else { - mLastRectRotation = 0; + mActiveTouchRotation = 0; mQuickStepStartingRotation = QUICKSTEP_ROTATION_UNINITIALIZED; } resetSwipeRegions(info); } + /** + * Call when removing multiple regions to swipe from, but still in active quickswitch mode (task + * list is still frozen). + * Ex. This would be called when user has quickswitched to the same app rotation that + * they started quickswitching in, indicating that extra nav regions can be ignored. Calling + * this will update the value of {@link #mActiveTouchRotation} + * + * @param displayInfo The display whos rotation will be used as the current active rotation + */ + void setSingleActiveRegion(DefaultDisplay.Info displayInfo) { + mActiveTouchRotation = displayInfo.rotation; + resetSwipeRegions(displayInfo); + } + /** * Only saves the swipe region represented by {@param region}, clears the * rest from {@link #mSwipeTouchRegions} @@ -258,7 +272,7 @@ class OrientationTouchTransformer { } int getCurrentActiveRotation() { - return mLastRectRotation; + return mActiveTouchRotation; } int getQuickStepStartingRotation() { @@ -303,8 +317,9 @@ class OrientationTouchTransformer { Log.d(TestProtocol.NO_SWIPE_TO_HOME, "setting mLastRectTouched"); } mLastRectTouched = rect; - mLastRectRotation = rect.mRotation; - if (mEnableMultipleRegions && mCurrentDisplayRotation == mLastRectRotation) { + mActiveTouchRotation = rect.mRotation; + if (mEnableMultipleRegions + && mCurrentDisplayRotation == mActiveTouchRotation) { // TODO(b/154580671) might make this block unnecessary // Start a touch session for the default nav region for the display mQuickStepStartingRotation = mLastRectTouched.mRotation; diff --git a/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java b/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java index 79b38f23e1..0a70bd6cfe 100644 --- a/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java +++ b/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java @@ -151,7 +151,7 @@ public class RecentsAnimationDeviceState implements * sysui to adjust the navbar. */ private OrientationEventListener mOrientationListener; - private int mPreviousRotation = ROTATION_0; + private int mSensorRotation = ROTATION_0; /** * This is the configuration of the foreground app or the app that will be in the foreground * once a quickstep gesture finishes. @@ -246,18 +246,18 @@ public class RecentsAnimationDeviceState implements @Override public void onOrientationChanged(int degrees) { int newRotation = RecentsOrientedState.getRotationForUserDegreesRotated(degrees, - mPreviousRotation); - if (newRotation == mPreviousRotation) { + mSensorRotation); + if (newRotation == mSensorRotation) { return; } - mPreviousRotation = newRotation; + mSensorRotation = newRotation; mPrioritizeDeviceRotation = true; if (newRotation == mCurrentAppRotation) { // When user rotates device to the orientation of the foreground app after // quickstepping - toggleSecondaryNavBarsForRotation(false); + toggleSecondaryNavBarsForRotation(); } } }; @@ -339,14 +339,16 @@ public class RecentsAnimationDeviceState implements mCurrentAppRotation = mDisplayRotation; /* Update nav bars on the following: - * a) if we're not expecting quickswitch, this is coming from an activity rotation - * b) we launch an app in the orientation that user is already in - * c) We're not in overview, since overview will always be portrait (w/o home rotation) + * a) if this is coming from an activity rotation OR + * aa) we launch an app in the orientation that user is already in + * b) We're not in overview, since overview will always be portrait (w/o home rotation) + * c) We're actively in quickswitch mode */ if ((mPrioritizeDeviceRotation - || mCurrentAppRotation == mPreviousRotation) // switch to an app of orientation user is in - && !mInOverview) { - toggleSecondaryNavBarsForRotation(false); + || mCurrentAppRotation == mSensorRotation) // switch to an app of orientation user is in + && !mInOverview + && mTaskListFrozen) { + toggleSecondaryNavBarsForRotation(); } } @@ -461,7 +463,9 @@ public class RecentsAnimationDeviceState implements * @return whether SystemUI is in a state where we can start a system gesture. */ public boolean canStartSystemGesture() { - return (mSystemUiStateFlags & SYSUI_STATE_NAV_BAR_HIDDEN) == 0 + boolean canStartWithNavHidden = (mSystemUiStateFlags & SYSUI_STATE_NAV_BAR_HIDDEN) == 0 + || mTaskListFrozen; + return canStartWithNavHidden && (mSystemUiStateFlags & SYSUI_STATE_NOTIFICATION_PANEL_EXPANDED) == 0 && (mSystemUiStateFlags & SYSUI_STATE_QUICK_SETTINGS_EXPANDED) == 0 && ((mSystemUiStateFlags & SYSUI_STATE_HOME_DISABLED) == 0 @@ -634,29 +638,26 @@ public class RecentsAnimationDeviceState implements } private void enableMultipleRegions(boolean enable) { - toggleSecondaryNavBarsForRotation(enable); - if (enable && !TestProtocol.sDisableSensorRotation) { + mOrientationTouchTransformer.enableMultipleRegions(enable, mDefaultDisplay.getInfo()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getQuickStepStartingRotation()); + if (enable && !mInOverview && !TestProtocol.sDisableSensorRotation) { + // Clear any previous state from sensor manager + mSensorRotation = mCurrentAppRotation; mOrientationListener.enable(); } else { mOrientationListener.disable(); } } - private void notifySysuiForRotation(int rotation) { - UI_HELPER_EXECUTOR.execute(() -> - SystemUiProxy.INSTANCE.get(mContext).onQuickSwitchToNewTask(rotation)); - } - public void onStartGesture() { if (mTaskListFrozen) { // Prioritize whatever nav bar user touches once in quickstep // This case is specifically when user changes what nav bar they are using mid // quickswitch session before tasks list is unfrozen - notifySysuiForRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); } } - void onEndTargetCalculated(GestureState.GestureEndTarget endTarget, BaseActivityInterface activityInterface) { if (endTarget == GestureState.GestureEndTarget.RECENTS) { @@ -673,7 +674,8 @@ public class RecentsAnimationDeviceState implements // First gesture to start quickswitch enableMultipleRegions(true); } else { - notifySysuiForRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); + notifySysuiOfCurrentRotation( + mOrientationTouchTransformer.getCurrentActiveRotation()); } // A new gesture is starting, reset the current device rotation @@ -685,7 +687,7 @@ public class RecentsAnimationDeviceState implements // touched nav bar but didn't go anywhere and not quickswitching, do nothing return; } - notifySysuiForRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); } } @@ -697,13 +699,10 @@ public class RecentsAnimationDeviceState implements /** * Disables/Enables multiple nav bars on {@link OrientationTouchTransformer} and then * notifies system UI of the primary rotation the user is interacting with - * - * @param enable if {@code true}, this will report to sysUI the navbar of the region the gesture - * started in (during ACTION_DOWN), otherwise will report {@param displayRotation} */ - private void toggleSecondaryNavBarsForRotation(boolean enable) { - mOrientationTouchTransformer.enableMultipleRegions(enable, mDefaultDisplay.getInfo()); - notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getQuickStepStartingRotation()); + private void toggleSecondaryNavBarsForRotation() { + mOrientationTouchTransformer.setSingleActiveRegion(mDefaultDisplay.getInfo()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); } public int getCurrentActiveRotation() { From d92946356ecbb80aecedc375754c4ce8a1896d7b Mon Sep 17 00:00:00 2001 From: Vinit Nayak Date: Fri, 19 Jun 2020 19:10:31 -0700 Subject: [PATCH 09/12] Prevent premature resetting of quickswitch mode Previously, whenever a user returned to the same rotation that they had started quickswitch in, we were sending sysui the reset flag(-1) indicating that quickstep was complete instead of sending the rotation of the device the user was in. This was intentional and it worked, however we now always send the active rotation while the user is in a quickswitch session because sysui needs to show the fake home handle for immersive apps, which can occur in any rotation. This state is distinct from not being in quickswitch at all, in which no fake handles are shown. Fixes: 158677967 Change-Id: I910324abf781b4b30fe981139712bcb5b653c318 (cherry picked from commit f2daafcdf8b2ef54ca4f8654b124c5cc4a644782) --- .../OrientationTouchTransformer.java | 35 ++++++++---- .../RecentsAnimationDeviceState.java | 57 +++++++++---------- 2 files changed, 53 insertions(+), 39 deletions(-) diff --git a/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java b/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java index 3375c53124..cf5659c7d4 100644 --- a/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java +++ b/quickstep/src/com/android/quickstep/OrientationTouchTransformer.java @@ -68,13 +68,13 @@ class OrientationTouchTransformer { private Resources mResources; private OrientationRectF mLastRectTouched; /** - * The rotation of the last touched nav bar. Derived from {@link #mLastRectTouched}, but has a - * longer lifetime than the rect. Note this is different than {@link #mQuickStepStartingRotation} - * as it always updates its value on every touch whereas mQuickstepStartingRotation only - * updates when device rotation matches touch rotation. Maybe this will be only one necessary - * after TODO(b/154580671) is in. TBD. + * The rotation of the last touched nav bar, whether that be through the last region the user + * touched down on or valid rotation user turned their device to. + * Note this is different than + * {@link #mQuickStepStartingRotation} as it always updates its value on every touch whereas + * mQuickstepStartingRotation only updates when device rotation matches touch rotation. */ - private int mLastRectRotation; + private int mActiveTouchRotation; private SysUINavigationMode.Mode mMode; private QuickStepContractInfo mContractInfo; @@ -159,12 +159,26 @@ class OrientationTouchTransformer { if (mEnableMultipleRegions) { mQuickStepStartingRotation = info.rotation; } else { - mLastRectRotation = 0; + mActiveTouchRotation = 0; mQuickStepStartingRotation = QUICKSTEP_ROTATION_UNINITIALIZED; } resetSwipeRegions(info); } + /** + * Call when removing multiple regions to swipe from, but still in active quickswitch mode (task + * list is still frozen). + * Ex. This would be called when user has quickswitched to the same app rotation that + * they started quickswitching in, indicating that extra nav regions can be ignored. Calling + * this will update the value of {@link #mActiveTouchRotation} + * + * @param displayInfo The display whos rotation will be used as the current active rotation + */ + void setSingleActiveRegion(DefaultDisplay.Info displayInfo) { + mActiveTouchRotation = displayInfo.rotation; + resetSwipeRegions(displayInfo); + } + /** * Only saves the swipe region represented by {@param region}, clears the * rest from {@link #mSwipeTouchRegions} @@ -258,7 +272,7 @@ class OrientationTouchTransformer { } int getCurrentActiveRotation() { - return mLastRectRotation; + return mActiveTouchRotation; } int getQuickStepStartingRotation() { @@ -303,8 +317,9 @@ class OrientationTouchTransformer { Log.d(TestProtocol.NO_SWIPE_TO_HOME, "setting mLastRectTouched"); } mLastRectTouched = rect; - mLastRectRotation = rect.mRotation; - if (mEnableMultipleRegions && mCurrentDisplayRotation == mLastRectRotation) { + mActiveTouchRotation = rect.mRotation; + if (mEnableMultipleRegions + && mCurrentDisplayRotation == mActiveTouchRotation) { // TODO(b/154580671) might make this block unnecessary // Start a touch session for the default nav region for the display mQuickStepStartingRotation = mLastRectTouched.mRotation; diff --git a/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java b/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java index 79b38f23e1..0a70bd6cfe 100644 --- a/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java +++ b/quickstep/src/com/android/quickstep/RecentsAnimationDeviceState.java @@ -151,7 +151,7 @@ public class RecentsAnimationDeviceState implements * sysui to adjust the navbar. */ private OrientationEventListener mOrientationListener; - private int mPreviousRotation = ROTATION_0; + private int mSensorRotation = ROTATION_0; /** * This is the configuration of the foreground app or the app that will be in the foreground * once a quickstep gesture finishes. @@ -246,18 +246,18 @@ public class RecentsAnimationDeviceState implements @Override public void onOrientationChanged(int degrees) { int newRotation = RecentsOrientedState.getRotationForUserDegreesRotated(degrees, - mPreviousRotation); - if (newRotation == mPreviousRotation) { + mSensorRotation); + if (newRotation == mSensorRotation) { return; } - mPreviousRotation = newRotation; + mSensorRotation = newRotation; mPrioritizeDeviceRotation = true; if (newRotation == mCurrentAppRotation) { // When user rotates device to the orientation of the foreground app after // quickstepping - toggleSecondaryNavBarsForRotation(false); + toggleSecondaryNavBarsForRotation(); } } }; @@ -339,14 +339,16 @@ public class RecentsAnimationDeviceState implements mCurrentAppRotation = mDisplayRotation; /* Update nav bars on the following: - * a) if we're not expecting quickswitch, this is coming from an activity rotation - * b) we launch an app in the orientation that user is already in - * c) We're not in overview, since overview will always be portrait (w/o home rotation) + * a) if this is coming from an activity rotation OR + * aa) we launch an app in the orientation that user is already in + * b) We're not in overview, since overview will always be portrait (w/o home rotation) + * c) We're actively in quickswitch mode */ if ((mPrioritizeDeviceRotation - || mCurrentAppRotation == mPreviousRotation) // switch to an app of orientation user is in - && !mInOverview) { - toggleSecondaryNavBarsForRotation(false); + || mCurrentAppRotation == mSensorRotation) // switch to an app of orientation user is in + && !mInOverview + && mTaskListFrozen) { + toggleSecondaryNavBarsForRotation(); } } @@ -461,7 +463,9 @@ public class RecentsAnimationDeviceState implements * @return whether SystemUI is in a state where we can start a system gesture. */ public boolean canStartSystemGesture() { - return (mSystemUiStateFlags & SYSUI_STATE_NAV_BAR_HIDDEN) == 0 + boolean canStartWithNavHidden = (mSystemUiStateFlags & SYSUI_STATE_NAV_BAR_HIDDEN) == 0 + || mTaskListFrozen; + return canStartWithNavHidden && (mSystemUiStateFlags & SYSUI_STATE_NOTIFICATION_PANEL_EXPANDED) == 0 && (mSystemUiStateFlags & SYSUI_STATE_QUICK_SETTINGS_EXPANDED) == 0 && ((mSystemUiStateFlags & SYSUI_STATE_HOME_DISABLED) == 0 @@ -634,29 +638,26 @@ public class RecentsAnimationDeviceState implements } private void enableMultipleRegions(boolean enable) { - toggleSecondaryNavBarsForRotation(enable); - if (enable && !TestProtocol.sDisableSensorRotation) { + mOrientationTouchTransformer.enableMultipleRegions(enable, mDefaultDisplay.getInfo()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getQuickStepStartingRotation()); + if (enable && !mInOverview && !TestProtocol.sDisableSensorRotation) { + // Clear any previous state from sensor manager + mSensorRotation = mCurrentAppRotation; mOrientationListener.enable(); } else { mOrientationListener.disable(); } } - private void notifySysuiForRotation(int rotation) { - UI_HELPER_EXECUTOR.execute(() -> - SystemUiProxy.INSTANCE.get(mContext).onQuickSwitchToNewTask(rotation)); - } - public void onStartGesture() { if (mTaskListFrozen) { // Prioritize whatever nav bar user touches once in quickstep // This case is specifically when user changes what nav bar they are using mid // quickswitch session before tasks list is unfrozen - notifySysuiForRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); } } - void onEndTargetCalculated(GestureState.GestureEndTarget endTarget, BaseActivityInterface activityInterface) { if (endTarget == GestureState.GestureEndTarget.RECENTS) { @@ -673,7 +674,8 @@ public class RecentsAnimationDeviceState implements // First gesture to start quickswitch enableMultipleRegions(true); } else { - notifySysuiForRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); + notifySysuiOfCurrentRotation( + mOrientationTouchTransformer.getCurrentActiveRotation()); } // A new gesture is starting, reset the current device rotation @@ -685,7 +687,7 @@ public class RecentsAnimationDeviceState implements // touched nav bar but didn't go anywhere and not quickswitching, do nothing return; } - notifySysuiForRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); } } @@ -697,13 +699,10 @@ public class RecentsAnimationDeviceState implements /** * Disables/Enables multiple nav bars on {@link OrientationTouchTransformer} and then * notifies system UI of the primary rotation the user is interacting with - * - * @param enable if {@code true}, this will report to sysUI the navbar of the region the gesture - * started in (during ACTION_DOWN), otherwise will report {@param displayRotation} */ - private void toggleSecondaryNavBarsForRotation(boolean enable) { - mOrientationTouchTransformer.enableMultipleRegions(enable, mDefaultDisplay.getInfo()); - notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getQuickStepStartingRotation()); + private void toggleSecondaryNavBarsForRotation() { + mOrientationTouchTransformer.setSingleActiveRegion(mDefaultDisplay.getInfo()); + notifySysuiOfCurrentRotation(mOrientationTouchTransformer.getCurrentActiveRotation()); } public int getCurrentActiveRotation() { From 98ef53458d086ba69881c24946f0b3ebd4ea17df Mon Sep 17 00:00:00 2001 From: Sreyas Date: Tue, 23 Jun 2020 15:34:50 -0700 Subject: [PATCH 10/12] Fixing TaskMenu positioning. Bug: 159728554 Change-Id: I4a666363f092b5416edecd0731a0f448916c8def --- .../src/com/android/quickstep/views/TaskMenuView.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/views/TaskMenuView.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/views/TaskMenuView.java index 512bbac6bb..ef66b7a396 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/views/TaskMenuView.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/views/TaskMenuView.java @@ -235,7 +235,8 @@ public class TaskMenuView extends AbstractFloatingView { Rect insets = mActivity.getDragLayer().getInsets(); BaseDragLayer.LayoutParams params = (BaseDragLayer.LayoutParams) getLayoutParams(); params.width = orientationHandler.getTaskMenuWidth(taskView.getThumbnail()); - params.gravity = Gravity.START; + // Gravity set to Left instead of Start as sTempRect.left measures Left distance not Start + params.gravity = Gravity.LEFT; setLayoutParams(params); setScaleX(taskView.getScaleX()); setScaleY(taskView.getScaleY()); From 6293af557571354be799b7736724dc2df5a043bf Mon Sep 17 00:00:00 2001 From: Samuel Fufa Date: Tue, 23 Jun 2020 12:53:37 -0700 Subject: [PATCH 11/12] Remove hotseat edu flag Launcher should not restrict user migration to a one time event if we want users to migrate their hotseat by enabling hotseat prediction from suggestion settings. Test: Manual Bug: 159731272 Change-Id: I0e42dd6b6cf6374928e5b399d121d17fe8024ae1 --- .../launcher3/hybridhotseat/HotseatEduController.java | 2 -- .../hybridhotseat/HotseatPredictionController.java | 10 +--------- 2 files changed, 1 insertion(+), 11 deletions(-) diff --git a/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatEduController.java b/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatEduController.java index a1218aeb86..4f95254a72 100644 --- a/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatEduController.java +++ b/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatEduController.java @@ -47,7 +47,6 @@ import java.util.stream.IntStream; */ public class HotseatEduController { - public static final String KEY_HOTSEAT_EDU_SEEN = "hotseat_edu_seen"; public static final String HOTSEAT_EDU_ACTION = "com.android.launcher3.action.SHOW_HYBRID_HOTSEAT_EDU"; public static final String SETTINGS_ACTION = @@ -229,7 +228,6 @@ public class HotseatEduController { void finishOnboarding() { mOnOnboardingComplete.run(); - mLauncher.getSharedPrefs().edit().putBoolean(KEY_HOTSEAT_EDU_SEEN, true).apply(); } void showDimissTip() { diff --git a/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatPredictionController.java b/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatPredictionController.java index 7334d80dd6..1dbb9e2d6b 100644 --- a/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatPredictionController.java +++ b/quickstep/recents_ui_overrides/src/com/android/launcher3/hybridhotseat/HotseatPredictionController.java @@ -154,14 +154,6 @@ public class HotseatPredictionController implements DragController.DragListener, } } - /** - * Returns whether or not user has seen hybrid hotseat education - */ - public boolean isEduSeen() { - return mLauncher.getSharedPrefs().getBoolean(HotseatEduController.KEY_HOTSEAT_EDU_SEEN, - false); - } - /** * Shows appropriate hotseat education based on prediction enabled and migration states. */ @@ -172,7 +164,7 @@ public class HotseatPredictionController implements DragController.DragListener, Snackbar.show(mLauncher, R.string.hotsaet_tip_prediction_disabled, R.string.hotseat_prediction_settings, null, () -> mLauncher.startActivity(getSettingsIntent())); - } else if (isEduSeen() || getPredictedIcons().size() >= (mHotSeatItemsCount + 1) / 2) { + } else if (getPredictedIcons().size() >= (mHotSeatItemsCount + 1) / 2) { showDiscoveryTip(); } else { HotseatEduController eduController = new HotseatEduController(mLauncher, From 20024f44471dcc8075ad198fd63de27559976820 Mon Sep 17 00:00:00 2001 From: Sreyas Date: Tue, 23 Jun 2020 16:31:34 -0700 Subject: [PATCH 12/12] Fixing NPE befre ActionsView first initialized. Bug: 159728260 Change-Id: I00e6f8fccf8057495f77873f2f0a1ab01e63ed23 (cherry picked from commit 88f1f2046cecb83cafb94e94cc356cf02c3b7890) --- .../src/com/android/quickstep/TaskOverlayFactory.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/TaskOverlayFactory.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/TaskOverlayFactory.java index 01936e4ac7..e9614d1351 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/TaskOverlayFactory.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/TaskOverlayFactory.java @@ -148,7 +148,7 @@ public class TaskOverlayFactory implements ResourceBasedOverride { boolean rotated) { final boolean isAllowedByPolicy = thumbnail.isRealSnapshot; - mActionsView.updateDisabledFlags(DISABLED_ROTATED, rotated); + getActionsView().updateDisabledFlags(DISABLED_ROTATED, rotated); getActionsView().setCallbacks(new OverlayUICallbacks() { @Override