From be8b9eb16d4ea749fcf86c5cae1b334598aaa951 Mon Sep 17 00:00:00 2001 From: Ben Lin Date: Wed, 8 Jul 2020 18:45:35 -0700 Subject: [PATCH] Add ability to change PiP menu icon locations on the fly. This CL does: - Add a PipMenuIconsAlgorithm, allowing calculation on the fly for correct locations of individual icons - Make it so that when PIP changes its bounds, it updates the location of the action items accordingly (if needed) Bug: 160825579 Test: enter PIP, icons are still where they are Change-Id: I8618f7c5c36c8e09613c126c1ebb20b60e95de58 --- .../Shell/res/layout/pip_menu_activity.xml | 42 +++++---- libs/WindowManager/Shell/res/values/dimen.xml | 3 +- .../dagger/SystemUIRootComponent.java | 6 ++ .../systemui/pip/PipTaskOrganizer.java | 3 + .../systemui/pip/phone/PipMenuActivity.java | 19 ++++ .../pip/phone/PipMenuActivityController.java | 16 ++++ .../pip/phone/PipMenuIconsAlgorithm.java | 90 +++++++++++++++++++ .../systemui/pip/phone/PipMotionHelper.java | 10 ++- .../systemui/pip/phone/PipTouchHandler.java | 2 +- 9 files changed, 169 insertions(+), 22 deletions(-) create mode 100644 packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuIconsAlgorithm.java diff --git a/libs/WindowManager/Shell/res/layout/pip_menu_activity.xml b/libs/WindowManager/Shell/res/layout/pip_menu_activity.xml index 18064b547d4de..2e0a5e09e34f2 100644 --- a/libs/WindowManager/Shell/res/layout/pip_menu_activity.xml +++ b/libs/WindowManager/Shell/res/layout/pip_menu_activity.xml @@ -62,25 +62,30 @@ - - - + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:orientation="horizontal"> + + + + diff --git a/libs/WindowManager/Shell/res/values/dimen.xml b/libs/WindowManager/Shell/res/values/dimen.xml index 48c3cad596f1d..1c1217681b9f5 100644 --- a/libs/WindowManager/Shell/res/values/dimen.xml +++ b/libs/WindowManager/Shell/res/values/dimen.xml @@ -52,7 +52,8 @@ 48dp - + 12dp 4dp + 0dp diff --git a/packages/SystemUI/src/com/android/systemui/dagger/SystemUIRootComponent.java b/packages/SystemUI/src/com/android/systemui/dagger/SystemUIRootComponent.java index 6b8fcd562e6f7..e5cc1384efa4a 100644 --- a/packages/SystemUI/src/com/android/systemui/dagger/SystemUIRootComponent.java +++ b/packages/SystemUI/src/com/android/systemui/dagger/SystemUIRootComponent.java @@ -29,6 +29,7 @@ import com.android.systemui.dump.DumpManager; import com.android.systemui.fragments.FragmentService; import com.android.systemui.keyguard.KeyguardSliceProvider; import com.android.systemui.onehanded.dagger.OneHandedModule; +import com.android.systemui.pip.phone.PipMenuActivity; import com.android.systemui.pip.phone.dagger.PipModule; import com.android.systemui.statusbar.policy.ConfigurationController; import com.android.systemui.util.InjectionInflationController; @@ -121,4 +122,9 @@ public interface SystemUIRootComponent { * Member injection into the supplied argument. */ void inject(KeyguardSliceProvider keyguardSliceProvider); + + /** + * Member injection into the supplied argument. + */ + void inject(PipMenuActivity pipMenuActivity); } diff --git a/packages/SystemUI/src/com/android/systemui/pip/PipTaskOrganizer.java b/packages/SystemUI/src/com/android/systemui/pip/PipTaskOrganizer.java index 0d6b522046f7b..35e56ee879676 100644 --- a/packages/SystemUI/src/com/android/systemui/pip/PipTaskOrganizer.java +++ b/packages/SystemUI/src/com/android/systemui/pip/PipTaskOrganizer.java @@ -178,6 +178,9 @@ public class PipTaskOrganizer extends TaskOrganizer implements Rect startBounds = (Rect) args.arg2; Rect toBounds = (Rect) args.arg3; userResizePip(startBounds, toBounds); + if (updateBoundsCallback != null) { + updateBoundsCallback.accept(toBounds); + } break; } } diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivity.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivity.java index ad5a13e78cb49..d6f3e163ad70a 100644 --- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivity.java +++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivity.java @@ -76,12 +76,15 @@ import android.widget.ImageButton; import android.widget.LinearLayout; import com.android.systemui.Interpolators; +import com.android.systemui.SystemUIFactory; import com.android.wm.shell.R; import java.util.ArrayList; import java.util.Collections; import java.util.List; +import javax.inject.Inject; + /** * Translucent activity that gets started on top of a task in PIP to allow the user to control it. */ @@ -100,6 +103,7 @@ public class PipMenuActivity extends Activity { public static final int MESSAGE_POINTER_EVENT = 7; public static final int MESSAGE_MENU_EXPANDED = 8; public static final int MESSAGE_FADE_OUT_MENU = 9; + public static final int MESSAGE_UPDATE_MENU_LAYOUT = 10; private static final int INITIAL_DISMISS_DELAY = 3500; private static final int POST_INTERACTION_DISMISS_DELAY = 2000; @@ -129,8 +133,12 @@ public class PipMenuActivity extends Activity { private View mSettingsButton; private View mDismissButton; private View mResizeHandle; + private View mTopEndContainer; private int mBetweenActionPaddingLand; + @Inject + PipMenuIconsAlgorithm mPipMenuIconsAlgorithm; + private AnimatorSet mMenuContainerAnimator; private ValueAnimator.AnimatorUpdateListener mMenuBgUpdateListener = @@ -193,6 +201,11 @@ public class PipMenuActivity extends Activity { fadeOutMenu(); break; } + case MESSAGE_UPDATE_MENU_LAYOUT: { + final Rect bounds = (Rect) msg.obj; + mPipMenuIconsAlgorithm.onBoundsChanged(bounds); + break; + } } } }; @@ -208,6 +221,9 @@ public class PipMenuActivity extends Activity { getWindow().addFlags(LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH); super.onCreate(savedInstanceState); + + SystemUIFactory.getInstance().getRootComponent().inject(this); + setContentView(R.layout.pip_menu_activity); mAccessibilityManager = getSystemService(AccessibilityManager.class); @@ -217,6 +233,7 @@ public class PipMenuActivity extends Activity { mViewRoot.setBackground(mBackgroundDrawable); mMenuContainer = findViewById(R.id.menu_container); mMenuContainer.setAlpha(0); + mTopEndContainer = findViewById(R.id.top_end_container); mSettingsButton = findViewById(R.id.settings); mSettingsButton.setAlpha(0); mSettingsButton.setOnClickListener((v) -> { @@ -238,6 +255,8 @@ public class PipMenuActivity extends Activity { mBetweenActionPaddingLand = getResources().getDimensionPixelSize( R.dimen.pip_between_action_padding_land); + mPipMenuIconsAlgorithm.bindViews((ViewGroup) mViewRoot, (ViewGroup) mTopEndContainer, + mResizeHandle, mSettingsButton, mDismissButton); updateFromIntent(getIntent()); setTitle(R.string.pip_menu_title); setDisablePreviewScreenshots(true); diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivityController.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivityController.java index 87e66fdc375c0..267c5eacd1393 100644 --- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivityController.java +++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuActivityController.java @@ -574,6 +574,22 @@ public class PipMenuActivityController { } } + /** + * Tell the PIP Menu to recalculate its layout given its current position on the display. + */ + public void updateMenuLayout(Rect bounds) { + if (mToActivityMessenger != null) { + Message m = Message.obtain(); + m.what = PipMenuActivity.MESSAGE_UPDATE_MENU_LAYOUT; + m.obj = bounds; + try { + mToActivityMessenger.send(m); + } catch (RemoteException e) { + Log.e(TAG, "Could not dispatch touch event", e); + } + } + } + public void dump(PrintWriter pw, String prefix) { final String innerPrefix = prefix + " "; pw.println(prefix + TAG); diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuIconsAlgorithm.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuIconsAlgorithm.java new file mode 100644 index 0000000000000..69a04d8d3e22a --- /dev/null +++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMenuIconsAlgorithm.java @@ -0,0 +1,90 @@ +/* + * Copyright (C) 2020 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.pip.phone; + +import android.content.Context; +import android.graphics.Rect; +import android.util.Log; +import android.view.Gravity; +import android.view.View; +import android.view.ViewGroup; +import android.widget.FrameLayout; + +import javax.inject.Inject; + +/** + * Helper class to calculate and place the menu icons on the PIP Menu. + */ +public class PipMenuIconsAlgorithm { + + private static final String TAG = "PipMenuIconsAlgorithm"; + + private boolean mFinishedLayout = false; + protected ViewGroup mViewRoot; + protected ViewGroup mTopEndContainer; + protected View mDragHandle; + protected View mSettingsButton; + protected View mDismissButton; + + @Inject + public PipMenuIconsAlgorithm(Context context) { + } + + /** + * Bind the necessary views. + */ + public void bindViews(ViewGroup viewRoot, ViewGroup topEndContainer, View dragHandle, + View settingsButton, View dismissButton) { + mViewRoot = viewRoot; + mTopEndContainer = topEndContainer; + mDragHandle = dragHandle; + mSettingsButton = settingsButton; + mDismissButton = dismissButton; + } + + + /** + * Updates the position of the drag handle based on where the PIP window is on the screen. + */ + public void onBoundsChanged(Rect bounds) { + if (mViewRoot == null || mTopEndContainer == null || mDragHandle == null + || mSettingsButton == null || mDismissButton == null) { + Log.e(TAG, "One if the required views is null."); + } + + //We only need to calculate the layout once since it does not change. + if (!mFinishedLayout) { + mTopEndContainer.removeView(mSettingsButton); + mViewRoot.addView(mSettingsButton); + + setLayoutGravity(mDragHandle, Gravity.START | Gravity.TOP); + setLayoutGravity(mSettingsButton, Gravity.START | Gravity.TOP); + mFinishedLayout = true; + } + } + + /** + * Set the gravity on the given view. + */ + protected static void setLayoutGravity(View v, int gravity) { + if (v.getLayoutParams() instanceof FrameLayout.LayoutParams) { + FrameLayout.LayoutParams params = (FrameLayout.LayoutParams) v.getLayoutParams(); + params.gravity = gravity; + v.setLayoutParams(params); + } + } +} diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipMotionHelper.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMotionHelper.java index 9f0b1de21b522..ca3ef24654982 100644 --- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipMotionHelper.java +++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipMotionHelper.java @@ -127,7 +127,10 @@ public class PipMotionHelper implements PipAppOpsListener.Callback, new PhysicsAnimator.SpringConfig( SpringForce.STIFFNESS_LOW, SpringForce.DAMPING_RATIO_LOW_BOUNCY); - private final Consumer mUpdateBoundsCallback = mBounds::set; + private final Consumer mUpdateBoundsCallback = (Rect newBounds) -> { + mMenuController.updateMenuLayout(newBounds); + mBounds.set(newBounds); + }; /** * Whether we're springing to the touch event location (vs. moving it to that position @@ -248,7 +251,10 @@ public class PipMotionHelper implements PipAppOpsListener.Callback, mBounds.set(toBounds); } else { mTemporaryBounds.set(toBounds); - mPipTaskOrganizer.scheduleUserResizePip(mBounds, mTemporaryBounds, null); + mPipTaskOrganizer.scheduleUserResizePip(mBounds, mTemporaryBounds, + (Rect newBounds) -> { + mMenuController.updateMenuLayout(newBounds); + }); } } else { // If PIP is 'catching up' after being stuck in the dismiss target, update the animation diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchHandler.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchHandler.java index f4553fd3d7161..bd9ddc57ca199 100644 --- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchHandler.java +++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchHandler.java @@ -348,7 +348,7 @@ public class PipTouchHandler { } private boolean shouldShowResizeHandle() { - return !mPipBoundsHandler.hasSaveReentryBounds(); + return false; } public void setTouchGesture(PipTouchGesture gesture) {