Prevent PiP movement while the resize animation is running.
- This was causing numerous artifacts when the user starts touching while
transitioning into PiP where the move rects clobber the animating rect.
Bug: 35764922
Test: Try touching the PiP while it is entering or exiting PiP
Change-Id: I5a72b5bea694b01aab401d2bb78a493688a9c655
diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java
index ae402ef..e7256d1 100644
--- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java
+++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipManager.java
@@ -71,8 +71,15 @@
}
@Override
+ public void onPinnedStackAnimationStarted() {
+ // Disable touches while the animation is running
+ mTouchHandler.setTouchEnabled(false);
+ }
+
+ @Override
public void onPinnedStackAnimationEnded() {
- // TODO(winsonc): Disable touch interaction with the PiP until the animation ends
+ // Re-enable touches after the animation completes
+ mTouchHandler.setTouchEnabled(true);
}
@Override
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 d832810..4100b66 100644
--- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchHandler.java
+++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchHandler.java
@@ -181,6 +181,10 @@
registerInputConsumer();
}
+ public void setTouchEnabled(boolean enabled) {
+ mTouchState.setAllowTouches(enabled);
+ }
+
public void onActivityPinned() {
// Reset some states once we are pinned
if (mIsTappingThrough) {
@@ -294,6 +298,7 @@
// Fall through to clean up
}
case MotionEvent.ACTION_CANCEL: {
+ mTouchState.reset();
break;
}
}
@@ -418,6 +423,10 @@
@Override
public void onDown(PipTouchState touchState) {
+ if (!touchState.isUserInteracting()) {
+ return;
+ }
+
if (ENABLE_DRAG_TO_DISMISS) {
mDismissViewController.createDismissTarget();
mHandler.postDelayed(mShowDismissAffordance, SHOW_DISMISS_AFFORDANCE_DELAY);
@@ -426,6 +435,10 @@
@Override
boolean onMove(PipTouchState touchState) {
+ if (!touchState.isUserInteracting()) {
+ return false;
+ }
+
if (touchState.startedDragging()) {
mSavedSnapFraction = -1f;
}
@@ -458,6 +471,10 @@
@Override
public boolean onUp(PipTouchState touchState) {
+ if (!touchState.isUserInteracting()) {
+ return false;
+ }
+
try {
if (ENABLE_DRAG_TO_DISMISS) {
mHandler.removeCallbacks(mShowDismissAffordance);
diff --git a/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchState.java b/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchState.java
index 702ad0a..a317dc3 100644
--- a/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchState.java
+++ b/packages/SystemUI/src/com/android/systemui/pip/phone/PipTouchState.java
@@ -37,6 +37,7 @@
private final PointF mLastTouch = new PointF();
private final PointF mLastDelta = new PointF();
private final PointF mVelocity = new PointF();
+ private boolean mAllowTouches = true;
private boolean mIsUserInteracting = false;
private boolean mIsDragging = false;
private boolean mStartedDragging = false;
@@ -48,23 +49,41 @@
}
/**
+ * Resets this state.
+ */
+ public void reset() {
+ mAllowDraggingOffscreen = false;
+ mIsDragging = false;
+ mStartedDragging = false;
+ mIsUserInteracting = false;
+ }
+
+ /**
* Processess a given touch event and updates the state.
*/
public void onTouchEvent(MotionEvent ev) {
switch (ev.getAction()) {
case MotionEvent.ACTION_DOWN: {
+ if (!mAllowTouches) {
+ return;
+ }
+
// Initialize the velocity tracker
initOrResetVelocityTracker();
+
mActivePointerId = ev.getPointerId(0);
mLastTouch.set(ev.getX(), ev.getY());
mDownTouch.set(mLastTouch);
- mIsDragging = false;
- mStartedDragging = false;
mAllowDraggingOffscreen = true;
mIsUserInteracting = true;
break;
}
case MotionEvent.ACTION_MOVE: {
+ // Skip event if we did not start processing this touch gesture
+ if (!mIsUserInteracting) {
+ break;
+ }
+
// Update the velocity tracker
mVelocityTracker.addMovement(ev);
int pointerIndex = ev.findPointerIndex(mActivePointerId);
@@ -86,6 +105,11 @@
break;
}
case MotionEvent.ACTION_POINTER_UP: {
+ // Skip event if we did not start processing this touch gesture
+ if (!mIsUserInteracting) {
+ break;
+ }
+
// Update the velocity tracker
mVelocityTracker.addMovement(ev);
@@ -100,6 +124,11 @@
break;
}
case MotionEvent.ACTION_UP: {
+ // Skip event if we did not start processing this touch gesture
+ if (!mIsUserInteracting) {
+ break;
+ }
+
// Update the velocity tracker
mVelocityTracker.addMovement(ev);
mVelocityTracker.computeCurrentVelocity(1000,
@@ -112,7 +141,6 @@
// Fall through to clean up
}
case MotionEvent.ACTION_CANCEL: {
- mIsUserInteracting = false;
recycleVelocityTracker();
break;
}
@@ -171,6 +199,19 @@
}
/**
+ * Sets whether touching is currently allowed.
+ */
+ public void setAllowTouches(boolean allowTouches) {
+ mAllowTouches = allowTouches;
+
+ // If the user happens to touch down before this is sent from the system during a transition
+ // then block any additional handling by resetting the state now
+ if (mIsUserInteracting) {
+ reset();
+ }
+ }
+
+ /**
* Disallows dragging offscreen for the duration of the current gesture.
*/
public void setDisallowDraggingOffscreen() {
@@ -202,6 +243,7 @@
public void dump(PrintWriter pw, String prefix) {
final String innerPrefix = prefix + " ";
pw.println(prefix + TAG);
+ pw.println(innerPrefix + "mAllowTouches=" + mAllowTouches);
pw.println(innerPrefix + "mDownTouch=" + mDownTouch);
pw.println(innerPrefix + "mDownDelta=" + mDownDelta);
pw.println(innerPrefix + "mLastTouch=" + mLastTouch);
diff --git a/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java b/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java
index cda902b..1042356 100644
--- a/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java
+++ b/packages/SystemUI/src/com/android/systemui/recents/misc/SystemServicesProxy.java
@@ -154,6 +154,7 @@
public void onTaskSnapshotChanged(int taskId, TaskSnapshot snapshot) { }
public void onActivityPinned() { }
public void onPinnedActivityRestartAttempt(String launchedFromPackage) { }
+ public void onPinnedStackAnimationStarted() { }
public void onPinnedStackAnimationEnded() { }
public void onActivityForcedResizable(String packageName, int taskId) { }
public void onActivityDismissingDockedStack() { }
@@ -206,6 +207,12 @@
}
@Override
+ public void onPinnedStackAnimationStarted() throws RemoteException {
+ mHandler.removeMessages(H.ON_PINNED_STACK_ANIMATION_STARTED);
+ mHandler.sendEmptyMessage(H.ON_PINNED_STACK_ANIMATION_STARTED);
+ }
+
+ @Override
public void onPinnedStackAnimationEnded() throws RemoteException {
mHandler.removeMessages(H.ON_PINNED_STACK_ANIMATION_ENDED);
mHandler.sendEmptyMessage(H.ON_PINNED_STACK_ANIMATION_ENDED);
@@ -1219,6 +1226,7 @@
private static final int ON_ACTIVITY_FORCED_RESIZABLE = 6;
private static final int ON_ACTIVITY_DISMISSING_DOCKED_STACK = 7;
private static final int ON_TASK_PROFILE_LOCKED = 8;
+ private static final int ON_PINNED_STACK_ANIMATION_STARTED = 9;
@Override
public void handleMessage(Message msg) {
@@ -1248,6 +1256,12 @@
}
break;
}
+ case ON_PINNED_STACK_ANIMATION_STARTED: {
+ for (int i = mTaskStackListeners.size() - 1; i >= 0; i--) {
+ mTaskStackListeners.get(i).onPinnedStackAnimationStarted();
+ }
+ break;
+ }
case ON_PINNED_STACK_ANIMATION_ENDED: {
for (int i = mTaskStackListeners.size() - 1; i >= 0; i--) {
mTaskStackListeners.get(i).onPinnedStackAnimationEnded();