diff --git a/jdk/src/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java b/jdk/src/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java index e1e7c9c24c9..cec7c552b94 100644 --- a/jdk/src/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java +++ b/jdk/src/macosx/classes/sun/lwawt/macosx/CDragSourceContextPeer.java @@ -132,44 +132,31 @@ public final class CDragSourceContextPeer extends SunDragSourceContextPeer { this.setDefaultDragImage(component); // Get drag image (if any) as BufferedImage and convert that to CImage: - long dragImage; Point dragImageOffset; if (fDragImage != null) { - BufferedImage bi = (fDragImage instanceof BufferedImage ? (BufferedImage) fDragImage : null); - - if (bi == null) { - // Create a new buffered image: - int width = fDragImage.getWidth(null); - int height = fDragImage.getHeight(null); - bi = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB_PRE); - - // Draw drag image into the buffered image: - Graphics g = bi.getGraphics(); - g.drawImage(fDragImage, 0, 0, null); - g.dispose(); + try { + fDragCImage = CImage.getCreator().createFromImageImmediately(fDragImage); + } catch(Exception e) { + // image creation may fail for any reason + throw new InvalidDnDOperationException("Drag image can not be created."); } - /* TODO:BG - fDragCImage = CImage.getCreator().createImage(bi); - dragImage = fDragCImage.getNSImage(); */ - fDragCImage = null; - dragImage = 0L; + if (fDragCImage == null) { + throw new InvalidDnDOperationException("Drag image is not ready."); + } + dragImageOffset = fDragImageOffset; } else { fDragCImage = null; - dragImage = 0L; dragImageOffset = new Point(0, 0); } - // Get NS drag image instance if we have a drag image: - long nsDragImage = 0L; //TODO:BG (fDragCImage != null ? fDragCImage.getNSImage() : 0L); - try { // Create native dragging source: final long nativeDragSource = createNativeDragSource(component, peer, nativeWindowPtr, transferable, triggerEvent, (int) (dragOrigin.getX() + componentOffset.x), (int) (dragOrigin.getY() + componentOffset.y), extModifiers, - clickCount, timestamp, cursor, dragImage, dragImageOffset.x, dragImageOffset.y, + clickCount, timestamp, cursor, fDragCImage, dragImageOffset.x, dragImageOffset.y, getDragSourceContext().getSourceActions(), formats, formatMap); if (nativeDragSource == 0) @@ -495,7 +482,7 @@ public final class CDragSourceContextPeer extends SunDragSourceContextPeer { // Native support: private native long createNativeDragSource(Component component, ComponentPeer peer, long nativePeer, Transferable transferable, InputEvent triggerEvent, int dragPosX, int dragPosY, int extModifiers, int clickCount, long timestamp, - Cursor cursor, long nsDragImage, int dragImageOffsetX, int dragImageOffsetY, + Cursor cursor, CImage nsDragImage, int dragImageOffsetX, int dragImageOffsetY, int sourceActions, long[] formats, Map formatMap); private native void doDragging(long nativeDragSource); diff --git a/jdk/src/macosx/classes/sun/lwawt/macosx/CImage.java b/jdk/src/macosx/classes/sun/lwawt/macosx/CImage.java index 425bd2c3e81..d764b95a454 100644 --- a/jdk/src/macosx/classes/sun/lwawt/macosx/CImage.java +++ b/jdk/src/macosx/classes/sun/lwawt/macosx/CImage.java @@ -97,35 +97,55 @@ public class CImage extends CFRetainedResource { return createImageUsingNativeSize(nativeCreateNSImageFromImageName(name)); } - private static int[] imageToArray(Image image) { + private static int[] imageToArray(Image image, boolean prepareImage) { if (image == null) return null; - MediaTracker mt = new MediaTracker(new Label()); - final int id = 0; - mt.addImage(image, id); + if (prepareImage && !(image instanceof BufferedImage)) { + final MediaTracker mt = new MediaTracker(new Label()); + final int id = 0; + mt.addImage(image, id); - try { - mt.waitForID(id); - } catch (InterruptedException e) { - } + try { + mt.waitForID(id); + } catch (InterruptedException e) { + return null; + } - if (mt.isErrorID(id)) { - return null; + if (mt.isErrorID(id)) { + return null; + } } int w = image.getWidth(null); int h = image.getHeight(null); + + if (w < 0 || h < 0) { + return null; + } + BufferedImage bimg = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB_PRE); Graphics2D g2 = bimg.createGraphics(); g2.setComposite(AlphaComposite.Src); g2.drawImage(image, 0, 0, null); g2.dispose(); + return ((DataBufferInt)bimg.getRaster().getDataBuffer()).getData(); } + public CImage createFromImageImmediately(final Image image) { + int[] buffer = imageToArray(image, false); + + if (buffer == null) { + return null; + } + + return new CImage(nativeCreateNSImageFromArray(buffer, image.getWidth(null), + image.getHeight(null))); + } + // This is used to create a CImage from a Image public CImage createFromImage(final Image image) { - int[] buffer = imageToArray(image); + int[] buffer = imageToArray(image, true); if (buffer == null) { return null; } @@ -146,7 +166,7 @@ public class CImage extends CFRetainedResource { num = 0; for (Image img : images) { - buffers[num] = imageToArray(img); + buffers[num] = imageToArray(img, true); if (buffers[num] == null) { // Unable to process the image continue; diff --git a/jdk/src/macosx/native/sun/awt/CDragSource.h b/jdk/src/macosx/native/sun/awt/CDragSource.h index 224bba17a6b..7e880cb529e 100644 --- a/jdk/src/macosx/native/sun/awt/CDragSource.h +++ b/jdk/src/macosx/native/sun/awt/CDragSource.h @@ -63,7 +63,7 @@ transferable:(jobject)jtransferable triggerEvent:(jobject)jtrigger dragPosX:(jint)dragPosX dragPosY:(jint)dragPosY modifiers:(jint)extModifiers clickCount:(jint)clickCount timeStamp:(jlong)timeStamp cursor:(jobject)jcursor - dragImage:(jlong)jnsdragimage dragImageOffsetX:(jint)jdragimageoffsetx dragImageOffsetY:(jint)jdragimageoffsety + dragImage:(jobject)jnsdragimage dragImageOffsetX:(jint)jdragimageoffsetx dragImageOffsetY:(jint)jdragimageoffsety sourceActions:(jint)jsourceactions formats:(jlongArray)jformats formatMap:(jobject)jformatmap; - (void)removeFromView:(JNIEnv *)env; diff --git a/jdk/src/macosx/native/sun/awt/CDragSource.m b/jdk/src/macosx/native/sun/awt/CDragSource.m index 27f505eda91..cbfe6270ceb 100644 --- a/jdk/src/macosx/native/sun/awt/CDragSource.m +++ b/jdk/src/macosx/native/sun/awt/CDragSource.m @@ -70,6 +70,7 @@ static BOOL sIsJavaDragging; JNF_CLASS_CACHE(DataTransfererClass, "sun/awt/datatransfer/DataTransferer"); JNF_CLASS_CACHE(CDragSourceContextPeerClass, "sun/lwawt/macosx/CDragSourceContextPeer"); +JNF_CLASS_CACHE(CImageClass, "sun/lwawt/macosx/CImage"); static NSDragOperation sDragOperation; static NSPoint sDraggingLocation; @@ -87,7 +88,7 @@ static BOOL sNeedsEnter; transferable:(jobject)jtransferable triggerEvent:(jobject)jtrigger dragPosX:(jint)dragPosX dragPosY:(jint)dragPosY modifiers:(jint)extModifiers clickCount:(jint)clickCount timeStamp:(jlong)timeStamp cursor:(jobject)jcursor - dragImage:(jlong)jnsdragimage dragImageOffsetX:(jint)jdragimageoffsetx dragImageOffsetY:(jint)jdragimageoffsety + dragImage:(jobject)jnsdragimage dragImageOffsetX:(jint)jdragimageoffsetx dragImageOffsetY:(jint)jdragimageoffsety sourceActions:(jint)jsourceactions formats:(jlongArray)jformats formatMap:(jobject)jformatmap { self = [super init]; @@ -107,8 +108,14 @@ static BOOL sNeedsEnter; fTriggerEvent = JNFNewGlobalRef(env, jtrigger); fCursor = JNFNewGlobalRef(env, jcursor); - fDragImage = (NSImage*) jlong_to_ptr(jnsdragimage); // Double-casting prevents compiler 'different size' warning. - [fDragImage retain]; + if (jnsdragimage) { + JNF_MEMBER_CACHE(nsImagePtr, CImageClass, "ptr", "J"); + jlong imgPtr = JNFGetLongField(env, jnsdragimage, nsImagePtr); + fDragImage = (NSImage*) jlong_to_ptr(imgPtr); // Double-casting prevents compiler 'd$|// + + [fDragImage retain]; + } + fDragImageOffset = NSMakePoint(jdragimageoffsetx, jdragimageoffsety); fSourceActions = jsourceactions; diff --git a/jdk/src/macosx/native/sun/awt/CDragSourceContextPeer.m b/jdk/src/macosx/native/sun/awt/CDragSourceContextPeer.m index 80d296d2364..e2fedfe35df 100644 --- a/jdk/src/macosx/native/sun/awt/CDragSourceContextPeer.m +++ b/jdk/src/macosx/native/sun/awt/CDragSourceContextPeer.m @@ -39,7 +39,7 @@ JNIEXPORT jlong JNICALL Java_sun_lwawt_macosx_CDragSourceContextPeer_createNativeDragSource (JNIEnv *env, jobject jthis, jobject jcomponent, jobject jpeer, jlong jnativepeer, jobject jtransferable, jobject jtrigger, jint jdragposx, jint jdragposy, jint jextmodifiers, jint jclickcount, jlong jtimestamp, - jobject jcursor, jlong jnsdragimage, jint jdragimageoffsetx, jint jdragimageoffsety, + jobject jcursor, jobject jnsdragimage, jint jdragimageoffsetx, jint jdragimageoffsety, jint jsourceactions, jlongArray jformats, jobject jformatmap) { id controlObj = (id) jlong_to_ptr(jnativepeer); diff --git a/jdk/test/java/awt/dnd/ImageDecoratedDnDNegative/ImageDecoratedDnDNegative.java b/jdk/test/java/awt/dnd/ImageDecoratedDnDNegative/ImageDecoratedDnDNegative.java index d90923b61c3..9c49ed69ea2 100644 --- a/jdk/test/java/awt/dnd/ImageDecoratedDnDNegative/ImageDecoratedDnDNegative.java +++ b/jdk/test/java/awt/dnd/ImageDecoratedDnDNegative/ImageDecoratedDnDNegative.java @@ -25,7 +25,7 @@ /* test %W% %E% - @bug 4874070 + @bug 4874070 7146550 @summary Tests basic DnD functionality @author Your Name: Alexey Utkin area=dnd @run applet ImageDecoratedDnDNegative.html