Bullet-proofing the drag window initial animation.
It’s unlikely, but still possible that something interesting will happen during the 150 ms that DragWindows takes to slightly increase in size before it gets hidden and replaced by the framework DND drag shadow. This fix covers 2 possible events that can happen during that time: 1. The drag gets cancelled (for example because of an app uninstall). Here, we eliminate a crash. 2. The user starts dragging the shadow. Before, this would start scrolling the home page. Now, SystemDragDriver starts processing touch events exactly as the InternalDragDriver would, until the growing finishes. Afterwards, it switches to framework dragging. Bug: 22609426 Change-Id: I73cc09fea45fcdcc6b75b13be1347da3e7c95509
This commit is contained in:
@@ -46,11 +46,42 @@ public abstract class DragDriver {
|
||||
*/
|
||||
public abstract void onDragViewAnimationEnd();
|
||||
|
||||
public abstract boolean onTouchEvent(MotionEvent ev);
|
||||
public boolean onTouchEvent(MotionEvent ev) {
|
||||
final int action = ev.getAction();
|
||||
|
||||
switch (action) {
|
||||
case MotionEvent.ACTION_MOVE:
|
||||
mEventListener.onDriverDragMove(ev.getX(), ev.getY());
|
||||
break;
|
||||
case MotionEvent.ACTION_UP:
|
||||
mEventListener.onDriverDragMove(ev.getX(), ev.getY());
|
||||
mEventListener.onDriverDragEnd(ev.getX(), ev.getY(), null);
|
||||
break;
|
||||
case MotionEvent.ACTION_CANCEL:
|
||||
mEventListener.onDriverDragCancel();
|
||||
break;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public abstract boolean onDragEvent (DragEvent event);
|
||||
|
||||
public abstract boolean onInterceptTouchEvent(MotionEvent ev);
|
||||
|
||||
public boolean onInterceptTouchEvent(MotionEvent ev) {
|
||||
final int action = ev.getAction();
|
||||
|
||||
switch (action) {
|
||||
case MotionEvent.ACTION_UP:
|
||||
mEventListener.onDriverDragEnd(ev.getX(), ev.getY(), null);
|
||||
break;
|
||||
case MotionEvent.ACTION_CANCEL:
|
||||
mEventListener.onDriverDragCancel();
|
||||
break;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public static DragDriver create(
|
||||
DragController dragController, ItemInfo dragInfo, DragView dragView) {
|
||||
@@ -71,7 +102,7 @@ class SystemDragDriver extends DragDriver {
|
||||
private final Intent mDragIntent;
|
||||
|
||||
private final DragView mDragView;
|
||||
boolean mDragging = false;
|
||||
boolean mIsFrameworkDragActive = false;
|
||||
boolean mReceivedDropEvent = false;
|
||||
float mLastX = 0;
|
||||
float mLastY = 0;
|
||||
@@ -116,10 +147,10 @@ class SystemDragDriver extends DragDriver {
|
||||
final int flagOpaque = 1 << 9;
|
||||
final int flags = (mDragIntent != null ? flagGlobal : 0) | flagOpaque;
|
||||
|
||||
mDragging = true;
|
||||
mIsFrameworkDragActive = true;
|
||||
|
||||
if (!mDragView.startDrag(dragData, shadowBuilder, null, flags)) {
|
||||
mDragging = false;
|
||||
mIsFrameworkDragActive = false;
|
||||
mEventListener.onDriverDragCancel();
|
||||
return;
|
||||
}
|
||||
@@ -131,17 +162,17 @@ class SystemDragDriver extends DragDriver {
|
||||
|
||||
@Override
|
||||
public boolean onTouchEvent(MotionEvent ev) {
|
||||
return false;
|
||||
return !mIsFrameworkDragActive && super.onTouchEvent(ev);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onInterceptTouchEvent(MotionEvent ev) {
|
||||
return false;
|
||||
return !mIsFrameworkDragActive && super.onInterceptTouchEvent(ev);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onDragEvent (DragEvent event) {
|
||||
if (!mDragging) {
|
||||
if (!mIsFrameworkDragActive) {
|
||||
// We are interested only in drag events started by this driver.
|
||||
return false;
|
||||
}
|
||||
@@ -189,7 +220,7 @@ class SystemDragDriver extends DragDriver {
|
||||
new AnotherWindowDropTarget(mDragView.getContext()) : null;
|
||||
|
||||
mEventListener.onDriverDragEnd(mLastX, mLastY, dropTargetOverride);
|
||||
mDragging = false;
|
||||
mIsFrameworkDragActive = false;
|
||||
return true;
|
||||
|
||||
default:
|
||||
@@ -209,42 +240,6 @@ class InternalDragDriver extends DragDriver {
|
||||
@Override
|
||||
public void onDragViewAnimationEnd() {}
|
||||
|
||||
@Override
|
||||
public boolean onTouchEvent(MotionEvent ev) {
|
||||
final int action = ev.getAction();
|
||||
|
||||
switch (action) {
|
||||
case MotionEvent.ACTION_MOVE:
|
||||
mEventListener.onDriverDragMove(ev.getX(), ev.getY());
|
||||
break;
|
||||
case MotionEvent.ACTION_UP:
|
||||
mEventListener.onDriverDragMove(ev.getX(), ev.getY());
|
||||
mEventListener.onDriverDragEnd(ev.getX(), ev.getY(), null);
|
||||
break;
|
||||
case MotionEvent.ACTION_CANCEL:
|
||||
mEventListener.onDriverDragCancel();
|
||||
break;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onInterceptTouchEvent(MotionEvent ev) {
|
||||
final int action = ev.getAction();
|
||||
|
||||
switch (action) {
|
||||
case MotionEvent.ACTION_UP:
|
||||
mEventListener.onDriverDragEnd(ev.getX(), ev.getY(), null);
|
||||
break;
|
||||
case MotionEvent.ACTION_CANCEL:
|
||||
mEventListener.onDriverDragCancel();
|
||||
break;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onDragEvent (DragEvent event) { return false; }
|
||||
};
|
||||
|
||||
@@ -56,6 +56,7 @@ public class DragView extends View {
|
||||
private final DragController mDragController;
|
||||
private boolean mHasDrawn = false;
|
||||
@Thunk float mCrossFadeProgress = 0f;
|
||||
private boolean mAnimationCancelled = false;
|
||||
|
||||
ValueAnimator mAnim;
|
||||
private float mInitialScale = 1f;
|
||||
@@ -116,7 +117,9 @@ public class DragView extends View {
|
||||
mAnim.addListener(new AnimatorListenerAdapter() {
|
||||
@Override
|
||||
public void onAnimationEnd(Animator animation) {
|
||||
mDragController.onDragViewAnimationEnd();
|
||||
if (!mAnimationCancelled) {
|
||||
mDragController.onDragViewAnimationEnd();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
@@ -332,6 +335,7 @@ public class DragView extends View {
|
||||
}
|
||||
|
||||
public void cancelAnimation() {
|
||||
mAnimationCancelled = true;
|
||||
if (mAnim != null && mAnim.isRunning()) {
|
||||
mAnim.cancel();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user