8015455: java/awt/dnd/DisposeFrameOnDragCrash/DisposeFrameOnDragTest.java hangs on windows
authorpchelko
Fri, 13 Sep 2013 17:41:47 +0400
changeset 20130 5e4ae22bef47
parent 20129 6dc2b2aa47ac
child 20131 59be23579a61
8015455: java/awt/dnd/DisposeFrameOnDragCrash/DisposeFrameOnDragTest.java hangs on windows Reviewed-by: serb, anthony
jdk/src/share/classes/java/awt/dnd/DropTarget.java
jdk/src/share/classes/javax/swing/TransferHandler.java
--- a/jdk/src/share/classes/java/awt/dnd/DropTarget.java	Fri Sep 13 17:38:28 2013 +0400
+++ b/jdk/src/share/classes/java/awt/dnd/DropTarget.java	Fri Sep 13 17:41:47 2013 +0400
@@ -351,6 +351,8 @@
      * @see #isActive
      */
     public synchronized void dragEnter(DropTargetDragEvent dtde) {
+        isDraggingInside = true;
+
         if (!active) return;
 
         if (dtListener != null) {
@@ -421,6 +423,8 @@
      * @see #isActive
      */
     public synchronized void dragExit(DropTargetEvent dte) {
+        isDraggingInside = false;
+
         if (!active) return;
 
         if (dtListener != null && active) dtListener.dragExit(dte);
@@ -444,6 +448,8 @@
      * @see #isActive
      */
     public synchronized void drop(DropTargetDropEvent dtde) {
+        isDraggingInside = false;
+
         clearAutoscroll();
 
         if (dtListener != null && active)
@@ -533,6 +539,12 @@
             ((DropTargetPeer)nativePeer).removeDropTarget(this);
 
         componentPeer = nativePeer = null;
+
+        synchronized (this) {
+            if (isDraggingInside) {
+                dragExit(new DropTargetEvent(getDropTargetContext()));
+            }
+        }
     }
 
     /**
@@ -855,4 +867,9 @@
      */
 
     private transient FlavorMap flavorMap;
+
+    /*
+     * If the dragging is currently inside this drop target
+     */
+    private transient boolean isDraggingInside;
 }
--- a/jdk/src/share/classes/javax/swing/TransferHandler.java	Fri Sep 13 17:38:28 2013 +0400
+++ b/jdk/src/share/classes/javax/swing/TransferHandler.java	Fri Sep 13 17:41:47 2013 +0400
@@ -1268,6 +1268,14 @@
                     }
                 }
             }
+            if (!isActive()) {
+                // If the Drop target is inactive the dragExit will not be dispatched to the dtListener,
+                // so make sure that we clean up the dtListener anyway.
+                DropTargetListener dtListener = getDropTargetListener();
+                    if (dtListener != null && dtListener instanceof DropHandler) {
+                        ((DropHandler)dtListener).cleanup(false);
+                    }
+            }
         }
 
         public void drop(DropTargetDropEvent e) {