From b9522d334a9b233ebe50e0feaa66fc28ded035ad Mon Sep 17 00:00:00 2001 From: Vinit Nayak Date: Thu, 7 May 2020 23:22:22 -0700 Subject: [PATCH] Infer launcher rotation when initializing RecentsOrientedState fixes: 154776599 Change-Id: I9b95f7f96836a974be0fd1236547efb4b405fda5 --- .../quickstep/util/TaskViewSimulator.java | 13 +-- .../android/quickstep/views/RecentsView.java | 24 ++---- .../quickstep/util/RecentsOrientedState.java | 82 ++++++++++++------- .../android/quickstep/TaplTestsQuickstep.java | 13 +++ .../launcher3/logging/LoggerUtils.java | 14 ++++ 5 files changed, 87 insertions(+), 59 deletions(-) diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/util/TaskViewSimulator.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/util/TaskViewSimulator.java index 832f0e2dce..391dcaf2d6 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/util/TaskViewSimulator.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/util/TaskViewSimulator.java @@ -88,9 +88,6 @@ public class TaskViewSimulator implements TransformParams.BuilderProxy { mSizeStrategy = sizeStrategy; mOrientationState = new RecentsOrientedState(context, sizeStrategy, i -> { }); - // We do not need to attach listeners as the simulator is created just for the gesture - // duration, and any settings are unlikely to change during this - mOrientationState.initWithoutListeners(); mCurrentFullscreenParams = new FullscreenDrawParams(context); mPageSpacing = context.getResources().getDimensionPixelSize(R.dimen.recents_page_spacing); @@ -109,15 +106,7 @@ public class TaskViewSimulator implements TransformParams.BuilderProxy { * @see com.android.quickstep.views.RecentsView#setLayoutRotation(int, int) */ public void setLayoutRotation(int touchRotation, int displayRotation) { - int launcherRotation; - if (!mOrientationState.isMultipleOrientationSupportedByDevice() - || mOrientationState.isHomeRotationAllowed()) { - launcherRotation = displayRotation; - } else { - launcherRotation = ROTATION_0; - } - - mOrientationState.update(touchRotation, displayRotation, launcherRotation); + mOrientationState.update(touchRotation, displayRotation); mLayoutValid = false; } diff --git a/quickstep/recents_ui_overrides/src/com/android/quickstep/views/RecentsView.java b/quickstep/recents_ui_overrides/src/com/android/quickstep/views/RecentsView.java index 49aca30146..31fc2fd948 100644 --- a/quickstep/recents_ui_overrides/src/com/android/quickstep/views/RecentsView.java +++ b/quickstep/recents_ui_overrides/src/com/android/quickstep/views/RecentsView.java @@ -16,6 +16,7 @@ package com.android.quickstep.views; +import static android.view.Surface.ROTATION_0; import static com.android.launcher3.BaseActivity.STATE_HANDLER_INVISIBILITY_FLAGS; import static com.android.launcher3.InvariantDeviceProfile.CHANGE_FLAG_ICON_PARAMS; import static com.android.launcher3.LauncherAnimUtils.SCALE_PROPERTY; @@ -55,7 +56,6 @@ import android.app.ActivityManager; import android.content.ComponentName; import android.content.Context; import android.content.Intent; -import android.content.res.Configuration; import android.graphics.Canvas; import android.graphics.Point; import android.graphics.PointF; @@ -509,7 +509,7 @@ public abstract class RecentsView extends PagedView impl mIPinnedStackAnimationListener.setActivity(mActivity); SystemUiProxy.INSTANCE.get(getContext()).setPinnedStackAnimationListener( mIPinnedStackAnimationListener); - mOrientationState.init(); + mOrientationState.initListeners(); } @Override @@ -524,7 +524,7 @@ public abstract class RecentsView extends PagedView impl mIdp.removeOnChangeListener(this); SystemUiProxy.INSTANCE.get(getContext()).setPinnedStackAnimationListener(null); mIPinnedStackAnimationListener.setActivity(null); - mOrientationState.destroy(); + mOrientationState.destroyListeners(); } @Override @@ -616,15 +616,6 @@ public abstract class RecentsView extends PagedView impl } } - @Override - protected void onConfigurationChanged(Configuration newConfig) { - super.onConfigurationChanged(newConfig); - int windowConfigurationRotation = ConfigurationCompat - .getWindowConfigurationRotation(getResources().getConfiguration()); - setLayoutInternal(mOrientationState.getTouchRotation(), - mOrientationState.getDisplayRotation(), windowConfigurationRotation); - } - @Override public boolean onTouchEvent(MotionEvent ev) { super.onTouchEvent(ev); @@ -1594,19 +1585,14 @@ public abstract class RecentsView extends PagedView impl } public void setLayoutRotation(int touchRotation, int displayRotation) { - int launcherRotation = mOrientationState.getLauncherRotation(); - setLayoutInternal(touchRotation, displayRotation, launcherRotation); - } - - private void setLayoutInternal(int touchRotation, int displayRotation, int launcherRotation) { - if (mOrientationState.update(touchRotation, displayRotation, launcherRotation)) { + if (mOrientationState.update(touchRotation, displayRotation)) { mOrientationHandler = mOrientationState.getOrientationHandler(); mIsRtl = mOrientationHandler.getRecentsRtlSetting(getResources()); setLayoutDirection(mIsRtl ? View.LAYOUT_DIRECTION_RTL : View.LAYOUT_DIRECTION_LTR); mClearAllButton.setRotation(mOrientationHandler.getDegreesRotated()); mActivity.getDragLayer().recreateControllers(); mActionsView.updateHiddenFlags(HIDDEN_NON_ZERO_ROTATION, - touchRotation != 0 || launcherRotation != 0); + touchRotation != 0 || mOrientationState.getLauncherRotation() != ROTATION_0); requestLayout(); } } diff --git a/quickstep/src/com/android/quickstep/util/RecentsOrientedState.java b/quickstep/src/com/android/quickstep/util/RecentsOrientedState.java index f6c4e666c6..1336561b3b 100644 --- a/quickstep/src/com/android/quickstep/util/RecentsOrientedState.java +++ b/quickstep/src/com/android/quickstep/util/RecentsOrientedState.java @@ -23,6 +23,7 @@ import static android.view.Surface.ROTATION_180; import static android.view.Surface.ROTATION_270; import static android.view.Surface.ROTATION_90; +import static com.android.launcher3.logging.LoggerUtils.extractObjectNameAndAddress; import static com.android.launcher3.states.RotationHelper.ALLOW_ROTATION_PREFERENCE_KEY; import static com.android.launcher3.util.Executors.UI_HELPER_EXECUTOR; @@ -84,7 +85,7 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre private @SurfaceRotation int mTouchRotation = ROTATION_0; private @SurfaceRotation int mDisplayRotation = ROTATION_0; - private @SurfaceRotation int mLauncherRotation = Surface.ROTATION_0; + private @SurfaceRotation int mLauncherRotation = ROTATION_0; // Launcher activity supports multiple orientation, but fallback activity does not private static final int FLAG_MULTIPLE_ORIENTATION_SUPPORTED_BY_ACTIVITY = 1 << 0; @@ -102,6 +103,8 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre private static final int FLAG_ROTATION_WATCHER_SUPPORTED = 1 << 6; // Whether to enable rotation watcher when multi-rotation is supported private static final int FLAG_ROTATION_WATCHER_ENABLED = 1 << 7; + // Enable home rotation for UI tests, ignoring home rotation value from prefs + private static final int FLAG_HOME_ROTATION_FORCE_ENABLED_FOR_TESTING = 1 << 8; private static final int MASK_MULTIPLE_ORIENTATION_SUPPORTED_BY_DEVICE = FLAG_MULTIPLE_ORIENTATION_SUPPORTED_BY_ACTIVITY @@ -163,6 +166,10 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre if (mOrientationListener.canDetectOrientation()) { mFlags |= FLAG_ROTATION_WATCHER_SUPPORTED; } + + // initialize external flags + updateAutoRotateSetting(); + updateHomeRotationSetting(); } /** @@ -181,13 +188,15 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre * false otherwise */ public boolean update( - @SurfaceRotation int touchRotation, @SurfaceRotation int displayRotation, - @SurfaceRotation int launcherRotation) { + @SurfaceRotation int touchRotation, @SurfaceRotation int displayRotation) { if (!isMultipleOrientationSupportedByDevice()) { return false; } - if (mDisplayRotation == displayRotation && mTouchRotation == touchRotation - && launcherRotation == mLauncherRotation) { + + int launcherRotation = inferLauncherRotation(displayRotation); + if (mDisplayRotation == displayRotation + && mTouchRotation == touchRotation + && mLauncherRotation == launcherRotation) { return false; } @@ -195,11 +204,10 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre mDisplayRotation = displayRotation; mTouchRotation = touchRotation; - if (canLauncherRotate() || mLauncherRotation == mTouchRotation) { - // TODO(b/153476489) Need to determine when launcher is rotated + if (mLauncherRotation == mTouchRotation) { mOrientationHandler = PagedOrientationHandler.HOME_ROTATED; if (DEBUG) { - Log.d(TAG, "Set Orientation Handler: " + mOrientationHandler); + Log.d(TAG, "current RecentsOrientedState: " + this); } return true; } @@ -212,11 +220,20 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre mOrientationHandler = PagedOrientationHandler.PORTRAIT; } if (DEBUG) { - Log.d(TAG, "Set Orientation Handler: " + mOrientationHandler); + Log.d(TAG, "current RecentsOrientedState: " + this); } return true; } + @SurfaceRotation + private int inferLauncherRotation(@SurfaceRotation int displayRotation) { + if (!isMultipleOrientationSupportedByDevice() || isHomeRotationAllowed()) { + return displayRotation; + } else { + return ROTATION_0; + } + } + private void setFlag(int mask, boolean enabled) { boolean wasRotationEnabled = !TestProtocol.sDisableSensorRotation && mFlags == VALUE_ROTATION_WATCHER_ENABLED; @@ -241,7 +258,9 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre @Override public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String s) { - updateHomeRotationSetting(); + if (ALLOW_ROTATION_PREFERENCE_KEY.equals(s)) { + updateHomeRotationSetting(); + } } private void updateAutoRotateSetting() { @@ -255,23 +274,24 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre } /** - * Initializes aany system values and registers corresponding change listeners. It must be - * paired with {@link #destroy()} call + * Initializes any system values and registers corresponding change listeners. It must be + * paired with {@link #destroyListeners()} call */ - public void init() { + public void initListeners() { if (isMultipleOrientationSupportedByDevice()) { mSharedPrefs.registerOnSharedPreferenceChangeListener(this); mContentResolver.registerContentObserver( Settings.System.getUriFor(Settings.System.ACCELEROMETER_ROTATION), false, mSystemAutoRotateObserver); } - initWithoutListeners(); + updateAutoRotateSetting(); + updateHomeRotationSetting(); } /** * Unregisters any previously registered listeners. */ - public void destroy() { + public void destroyListeners() { if (isMultipleOrientationSupportedByDevice()) { mSharedPrefs.unregisterOnSharedPreferenceChangeListener(this); mContentResolver.unregisterContentObserver(mSystemAutoRotateObserver); @@ -279,13 +299,8 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre setRotationWatcherEnabled(false); } - /** - * Initializes the OrientationState without attaching any listeners. This can be used when - * the object is short lived. - */ - public void initWithoutListeners() { - updateAutoRotateSetting(); - updateHomeRotationSetting(); + public void forceAllowRotationForTesting(boolean forceAllow) { + setFlag(FLAG_HOME_ROTATION_FORCE_ENABLED_FOR_TESTING, forceAllow); } @SurfaceRotation @@ -310,7 +325,8 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre public boolean isHomeRotationAllowed() { return (mFlags & (FLAG_HOME_ROTATION_ALLOWED_IN_PREFS | FLAG_MULTIWINDOW_ROTATION_ALLOWED)) - != 0; + != 0 || + (mFlags & FLAG_HOME_ROTATION_FORCE_ENABLED_FOR_TESTING) != 0; } public boolean canLauncherRotate() { @@ -440,9 +456,13 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre if (degrees < (90 - threshold)) { return ROTATION_0; } - if (degrees > (90 + threshold)) { + if (degrees > (90 + threshold) && degrees < 180) { return ROTATION_180; } + // flip from seascape to landscape + if (degrees > (180 + threshold) && degrees < 360) { + return ROTATION_90; + } break; case ROTATION_180: if (degrees < (180 - threshold)) { @@ -453,12 +473,16 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre } break; case ROTATION_90: - if (degrees < (270 - threshold)) { + if (degrees < (270 - threshold) && degrees > 90) { return ROTATION_180; } - if (degrees > (270 + threshold)) { + if (degrees > (270 + threshold) && degrees < 360) { return ROTATION_0; } + // flip from landscape to seascape + if (degrees > threshold && degrees < 180) { + return ROTATION_270; + } break; } @@ -506,13 +530,15 @@ public final class RecentsOrientedState implements SharedPreferences.OnSharedPre public String toString() { boolean systemRotationOn = (mFlags & FLAG_SYSTEM_ROTATION_ALLOWED) != 0; return "[" - + "mDisplayRotation=" + mDisplayRotation + + "this=" + extractObjectNameAndAddress(super.toString()) + + " mOrientationHandler=" + + extractObjectNameAndAddress(mOrientationHandler.toString()) + + " mDisplayRotation=" + mDisplayRotation + " mTouchRotation=" + mTouchRotation + " mLauncherRotation=" + mLauncherRotation + " mHomeRotation=" + isHomeRotationAllowed() + " mSystemRotation=" + systemRotationOn + " mFlags=" + mFlags - + " mOrientationHandler=" + mOrientationHandler + "]"; } } diff --git a/quickstep/tests/src/com/android/quickstep/TaplTestsQuickstep.java b/quickstep/tests/src/com/android/quickstep/TaplTestsQuickstep.java index 75fcfe2f19..bf093fdabf 100644 --- a/quickstep/tests/src/com/android/quickstep/TaplTestsQuickstep.java +++ b/quickstep/tests/src/com/android/quickstep/TaplTestsQuickstep.java @@ -42,6 +42,7 @@ import com.android.launcher3.ui.TaplTestsLauncher3; import com.android.quickstep.NavigationModeSwitchRule.NavigationModeSwitch; import com.android.quickstep.views.RecentsView; +import org.junit.After; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; @@ -53,6 +54,18 @@ public class TaplTestsQuickstep extends AbstractQuickStepTest { public void setUp() throws Exception { super.setUp(); TaplTestsLauncher3.initialize(this); + executeOnLauncher(launcher -> { + RecentsView recentsView = launcher.getOverviewPanel(); + recentsView.getPagedViewOrientedState().forceAllowRotationForTesting(true); + }); + } + + @After + public void tearDown() { + executeOnLauncher(launcher -> { + RecentsView recentsView = launcher.getOverviewPanel(); + recentsView.getPagedViewOrientedState().forceAllowRotationForTesting(false); + }); } private void startTestApps() throws Exception { diff --git a/src/com/android/launcher3/logging/LoggerUtils.java b/src/com/android/launcher3/logging/LoggerUtils.java index 0f79bd6fd6..cd4f034e83 100644 --- a/src/com/android/launcher3/logging/LoggerUtils.java +++ b/src/com/android/launcher3/logging/LoggerUtils.java @@ -41,6 +41,7 @@ public class LoggerUtils { private static final ArrayMap> sNameCache = new ArrayMap<>(); private static final String UNKNOWN = "UNKNOWN"; private static final int DEFAULT_PREDICTED_RANK = 10000; + private static final String DELIMITER_DOT = "\\."; public static String getFieldName(int value, Class c) { SparseArray cache; @@ -173,4 +174,17 @@ public class LoggerUtils { targets.toArray(targetsArray); return newLauncherEvent(action, targetsArray); } + + /** + * String conversion for only the helpful parts of {@link Object#toString()} method + * @param stringToExtract "foo.bar.baz.MyObject@1234" + * @return "MyObject@1234" + */ + public static String extractObjectNameAndAddress(String stringToExtract) { + String[] superStringParts = stringToExtract.split(DELIMITER_DOT); + if (superStringParts.length == 0) { + return ""; + } + return superStringParts[superStringParts.length - 1]; + } }