summaryrefslogtreecommitdiffstats
path: root/core
diff options
context:
space:
mode:
authorChris Tate <ctate@google.com>2010-11-03 12:00:56 -0700
committerAndroid (Google) Code Review <android-gerrit@google.com>2010-11-03 12:00:56 -0700
commit5f4b7d8a8a394940b49ecdd8b153a0eab9528c5c (patch)
tree32ebccd7439b1fd2240633b8091c465bc942e4e6 /core
parenta2773f51fdbf270b0ed6f8e7b11816487a9bb2fe (diff)
parent9d1ab883293b047b654935b84d0803c8c383be91 (diff)
downloadframeworks_base-5f4b7d8a8a394940b49ecdd8b153a0eab9528c5c.zip
frameworks_base-5f4b7d8a8a394940b49ecdd8b153a0eab9528c5c.tar.gz
frameworks_base-5f4b7d8a8a394940b49ecdd8b153a0eab9528c5c.tar.bz2
Merge "Fix drag enter/exit reporting"
Diffstat (limited to 'core')
-rw-r--r--core/java/android/view/ViewGroup.java44
-rw-r--r--core/java/android/view/ViewRoot.java17
2 files changed, 43 insertions, 18 deletions
diff --git a/core/java/android/view/ViewGroup.java b/core/java/android/view/ViewGroup.java
index 0f9312c..ad343a3 100644
--- a/core/java/android/view/ViewGroup.java
+++ b/core/java/android/view/ViewGroup.java
@@ -870,7 +870,7 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
switch (event.mAction) {
case DragEvent.ACTION_DRAG_STARTED: {
// clear state to recalculate which views we drag over
- root.setDragFocus(event, null);
+ mCurrentDragView = null;
// Now dispatch down to our children, caching the responses
mChildAcceptsDrag = false;
@@ -915,11 +915,28 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
final View target = findFrontmostDroppableChildAt(event.mX, event.mY, mLocalPoint);
// If we've changed apparent drag target, tell the view root which view
- // we're over now. This will in turn send out DRAG_ENTERED / DRAG_EXITED
- // notifications as appropriate.
+ // we're over now [for purposes of the eventual drag-recipient-changed
+ // notifications to the framework] and tell the new target that the drag
+ // has entered its bounds. The root will see setDragFocus() calls all
+ // the way down to the final leaf view that is handling the LOCATION event
+ // before reporting the new potential recipient to the framework.
if (mCurrentDragView != target) {
- root.setDragFocus(event, target);
+ root.setDragFocus(target);
+
+ final int action = event.mAction;
+ // If we've dragged off of a child view, send it the EXITED message
+ if (mCurrentDragView != null) {
+ event.mAction = DragEvent.ACTION_DRAG_EXITED;
+ mCurrentDragView.dispatchDragEvent(event);
+ }
mCurrentDragView = target;
+
+ // If we've dragged over a new child view, send it the ENTERED message
+ if (target != null) {
+ event.mAction = DragEvent.ACTION_DRAG_ENTERED;
+ target.dispatchDragEvent(event);
+ }
+ event.mAction = action; // restore the event's original state
}
// Dispatch the actual drag location notice, localized into its coordinates
@@ -934,6 +951,25 @@ public abstract class ViewGroup extends View implements ViewParent, ViewManager
}
} break;
+ /* Entered / exited dispatch
+ *
+ * DRAG_ENTERED is not dispatched downwards from ViewGroup. The reason for this is
+ * that we're about to get the corresponding LOCATION event, which we will use to
+ * determine which of our children is the new target; at that point we will
+ * push a DRAG_ENTERED down to the new target child [which may itself be a ViewGroup].
+ *
+ * DRAG_EXITED *is* dispatched all the way down immediately: once we know the
+ * drag has left this ViewGroup, we know by definition that every contained subview
+ * is also no longer under the drag point.
+ */
+
+ case DragEvent.ACTION_DRAG_EXITED: {
+ if (mCurrentDragView != null) {
+ mCurrentDragView.dispatchDragEvent(event);
+ mCurrentDragView = null;
+ }
+ } break;
+
case DragEvent.ACTION_DROP: {
if (ViewDebug.DEBUG_DRAG) Log.d(View.VIEW_LOG_TAG, "Drop event: " + event);
View target = findFrontmostDroppableChildAt(event.mX, event.mY, mLocalPoint);
diff --git a/core/java/android/view/ViewRoot.java b/core/java/android/view/ViewRoot.java
index 22a7773..c7c2071 100644
--- a/core/java/android/view/ViewRoot.java
+++ b/core/java/android/view/ViewRoot.java
@@ -2493,11 +2493,12 @@ public final class ViewRoot extends Handler implements ViewParent, View.AttachIn
// a window boundary, so the current drag target within this one must have
// just been exited. Send it the usual notifications and then we're done
// for now.
- setDragFocus(event, null);
+ mView.dispatchDragEvent(event);
} else {
// Cache the drag description when the operation starts, then fill it in
// on subsequent calls as a convenience
if (what == DragEvent.ACTION_DRAG_STARTED) {
+ mCurrentDragView = null; // Start the current-recipient tracking
mDragDescription = event.mClipDescription;
} else {
event.mClipDescription = mDragDescription;
@@ -2557,22 +2558,10 @@ public final class ViewRoot extends Handler implements ViewParent, View.AttachIn
outLocation.y = (int) mLastTouchPoint.y;
}
- public void setDragFocus(DragEvent event, View newDragTarget) {
- final int action = event.mAction;
- // If we've dragged off of a view, send it the EXITED message
+ public void setDragFocus(View newDragTarget) {
if (mCurrentDragView != newDragTarget) {
- if (mCurrentDragView != null) {
- event.mAction = DragEvent.ACTION_DRAG_EXITED;
- mCurrentDragView.dispatchDragEvent(event);
- }
mCurrentDragView = newDragTarget;
}
- // If we've dragged over a new view, send it the ENTERED message
- if (newDragTarget != null) {
- event.mAction = DragEvent.ACTION_DRAG_ENTERED;
- newDragTarget.dispatchDragEvent(event);
- }
- event.mAction = action; // restore the event's original state
}
private AudioManager getAudioManager() {