New tap on PiP window behavior

PiP window stays same on tap if it's large enough to hold all the
actions within it. Ignore the artifacts in demo video such as the shift
of settings button and menu resize out of sync, they are tracked in
separate bugs.

Video: http://rcll/aaaaaabFQoRHlzixHdtY/hkQgdmbuBhNT0WdKW8aegL
Bug: 175055101
Test: See video
Change-Id: Ie19b30dd1e8ba716095b76a3f341b5ab2a51399b
diff --git a/libs/WindowManager/Shell/res/layout/pip_menu.xml b/libs/WindowManager/Shell/res/layout/pip_menu.xml
index 2e0a5e0..b581f55 100644
--- a/libs/WindowManager/Shell/res/layout/pip_menu.xml
+++ b/libs/WindowManager/Shell/res/layout/pip_menu.xml
@@ -36,8 +36,8 @@
             android:layout_height="match_parent">
             <ImageButton
                 android:id="@+id/expand_button"
-                android:layout_width="60dp"
-                android:layout_height="60dp"
+                android:layout_width="@dimen/pip_expand_action_size"
+                android:layout_height="@dimen/pip_expand_action_size"
                 android:layout_gravity="center"
                 android:contentDescription="@string/pip_phone_expand"
                 android:padding="10dp"
diff --git a/libs/WindowManager/Shell/res/values/dimen.xml b/libs/WindowManager/Shell/res/values/dimen.xml
index e25a05c..034e65c 100644
--- a/libs/WindowManager/Shell/res/values/dimen.xml
+++ b/libs/WindowManager/Shell/res/values/dimen.xml
@@ -26,6 +26,9 @@
     <!-- The height of the PiP actions container in which the actions are vertically centered. -->
     <dimen name="pip_action_size">48dp</dimen>
 
+    <!-- The width and height of the PiP expand action. -->
+    <dimen name="pip_expand_action_size">60dp</dimen>
+
     <!-- The padding between actions in the PiP in landscape  Note that the PiP does not reflect
          the configuration of the device, so we can't use -land resources. -->
     <dimen name="pip_between_action_padding_land">8dp</dimen>
diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PhonePipMenuController.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PhonePipMenuController.java
index 8bf1b46..4b118f1 100644
--- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PhonePipMenuController.java
+++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PhonePipMenuController.java
@@ -34,6 +34,7 @@
 import android.os.IBinder;
 import android.os.RemoteException;
 import android.util.Log;
+import android.util.Size;
 import android.view.MotionEvent;
 import android.view.SurfaceControl;
 import android.view.SyncRtSurfaceTransactionApplier;
@@ -210,6 +211,11 @@
         }
     }
 
+    @Nullable
+    Size getEstimatedMenuSize() {
+        return mPipMenuView == null ? null : mPipMenuView.getEstimatedMenuSize();
+    }
+
     /**
      * When other components requests the menu controller directly to show the menu, we must
      * first fire off the request to the other listeners who will then propagate the call
@@ -224,13 +230,13 @@
      * Similar to {@link #showMenu(int, Rect, boolean, boolean, boolean)} but only show the menu
      * upon PiP window transition is finished.
      */
-    public void showMenuWithDelay(int menuState, Rect stackBounds, boolean allowMenuTimeout,
+    public void showMenuWithPossibleDelay(int menuState, Rect stackBounds, boolean allowMenuTimeout,
             boolean willResizeMenu, boolean showResizeHandle) {
         // hide all visible controls including close button and etc. first, this is to ensure
         // menu is totally invisible during the transition to eliminate unpleasant artifacts
         fadeOutMenu();
         showMenuInternal(menuState, stackBounds, allowMenuTimeout, willResizeMenu,
-                true /* withDelay */, showResizeHandle);
+                willResizeMenu /* withDelay=willResizeMenu here */, showResizeHandle);
     }
 
     /**
diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipMenuView.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipMenuView.java
index 2e515ee..48942b6 100644
--- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipMenuView.java
+++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipMenuView.java
@@ -48,6 +48,7 @@
 import android.os.UserHandle;
 import android.util.Log;
 import android.util.Pair;
+import android.util.Size;
 import android.view.KeyEvent;
 import android.view.LayoutInflater;
 import android.view.MotionEvent;
@@ -76,9 +77,6 @@
 
     private static final String TAG = "PipMenuView";
 
-    private static final int MESSAGE_INVALID_TYPE = -1;
-    public static final int MESSAGE_MENU_EXPANDED = 8;
-
     private static final int INITIAL_DISMISS_DELAY = 3500;
     private static final int POST_INTERACTION_DISMISS_DELAY = 2000;
     private static final long MENU_FADE_DURATION = 125;
@@ -86,8 +84,6 @@
     private static final long MENU_SHOW_ON_EXPAND_START_DELAY = 30;
 
     private static final float MENU_BACKGROUND_ALPHA = 0.3f;
-    private static final float DISMISS_BACKGROUND_ALPHA = 0.6f;
-
     private static final float DISABLED_ACTION_ALPHA = 0.54f;
 
     private static final boolean ENABLE_RESIZE_HANDLE = false;
@@ -370,6 +366,19 @@
         }
     }
 
+    /**
+     * @return estimated {@link Size} for which the width is based on number of actions and
+     *         height based on the height of expand button + top and bottom action bar.
+     */
+    Size getEstimatedMenuSize() {
+        final int pipActionSize = mContext.getResources().getDimensionPixelSize(
+                R.dimen.pip_action_size);
+        final int width = mActions.size() * pipActionSize;
+        final int height = pipActionSize * 2 + mContext.getResources().getDimensionPixelSize(
+                R.dimen.pip_expand_action_size);
+        return new Size(width, height);
+    }
+
     void setActions(Rect stackBounds, List<RemoteAction> actions) {
         mActions.clear();
         mActions.addAll(actions);
diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipTouchHandler.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipTouchHandler.java
index c9f5ae2..0ef49fe 100644
--- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipTouchHandler.java
+++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipTouchHandler.java
@@ -32,6 +32,7 @@
 import android.graphics.Rect;
 import android.os.Handler;
 import android.provider.DeviceConfig;
+import android.util.Log;
 import android.util.Size;
 import android.view.InputEvent;
 import android.view.MotionEvent;
@@ -176,7 +177,7 @@
         mPipDismissTargetHandler = new PipDismissTargetHandler(context, pipUiEventLogger,
                 mMotionHelper, mainExecutor);
         mTouchState = new PipTouchState(ViewConfiguration.get(context),
-                () -> mMenuController.showMenuWithDelay(MENU_STATE_FULL,
+                () -> mMenuController.showMenuWithPossibleDelay(MENU_STATE_FULL,
                         mPipBoundsState.getBounds(), true /* allowMenuTimeout */, willResizeMenu(),
                         shouldShowResizeHandle()),
                 menuController::hideMenu,
@@ -925,16 +926,21 @@
     }
 
     /**
-     * @return whether the menu will resize as a part of showing the full menu.
+     * @return {@code true} if the menu should be resized on tap because app explicitly specifies
+     * PiP window size that is too small to hold all the actions.
      */
     private boolean willResizeMenu() {
         if (!mEnableResize) {
             return false;
         }
-        return mPipBoundsState.getExpandedBounds().width()
-                != mPipBoundsState.getNormalBounds().width()
-                || mPipBoundsState.getExpandedBounds().height()
-                != mPipBoundsState.getNormalBounds().height();
+        final Size estimatedMenuSize = mMenuController.getEstimatedMenuSize();
+        if (estimatedMenuSize == null) {
+            Log.wtf(TAG, "Failed to get estimated menu size");
+            return false;
+        }
+        final Rect currentBounds = mPipBoundsState.getBounds();
+        return currentBounds.width() < estimatedMenuSize.getWidth()
+                || currentBounds.height() < estimatedMenuSize.getHeight();
     }
 
     /**