diff dwt/graphics/Image.d @ 45:d8635bb48c7c

Merge with SWT 3.5
author Jacob Carlborg <doob@me.com>
date Mon, 01 Dec 2008 17:07:00 +0100
parents db5a898b2119
children cfa563df4fdd
line wrap: on
line diff
--- a/dwt/graphics/Image.d	Tue Oct 21 15:20:04 2008 +0200
+++ b/dwt/graphics/Image.d	Mon Dec 01 17:07:00 2008 +0100
@@ -1,5 +1,5 @@
-/*******************************************************************************
- * Copyright (c) 2000, 2007 IBM Corporation and others.
+/*******************************************************************************
+ * Copyright (c) 2000, 2008 IBM Corporation and others.
  * All rights reserved. This program and the accompanying materials
  * are made available under the terms of the Eclipse Public License v1.0
  * which accompanies this distribution, and is available at
@@ -9,7 +9,7 @@
  *     IBM Corporation - initial API and implementation
  *     
  * Port to the D programming language:
- *     Jacob Carlborg <jacob.carlborg@gmail.com>
+ *     Jacob Carlborg <doob@me.com>
  *******************************************************************************/
 module dwt.graphics.Image;
 
@@ -19,13 +19,15 @@
 import dwt.DWT;
 import dwt.DWTError;
 import dwt.DWTException;
+import dwt.internal.C;
 import dwt.internal.cocoa.NSAffineTransform;
+import dwt.internal.cocoa.NSAutoreleasePool;
 import dwt.internal.cocoa.NSBitmapImageRep;
 import dwt.internal.cocoa.NSGraphicsContext;
 import dwt.internal.cocoa.NSImage;
 import dwt.internal.cocoa.NSImageRep;
 import dwt.internal.cocoa.NSSize;
-import dwt.internal.cocoa.NSString;
+import dwt.internal.cocoa.NSThread;
 import dwt.internal.cocoa.OS;
 
 import tango.text.convert.Format;
@@ -90,6 +92,9 @@
  * @see Color
  * @see ImageData
  * @see ImageLoader
+ * @see <a href="http://www.eclipse.org/swt/snippets/#image">Image snippets</a>
+ * @see <a href="http://www.eclipse.org/swt/examples.php">DWT Examples: GraphicsExample, ImageAnalyzer</a>
+ * @see <a href="http://www.eclipse.org/swt/">Sample code and further information</a>
  */
 public final class Image : Resource, Drawable {
 
@@ -191,8 +196,14 @@
  */
 public this(Device device, int width, int height) {
     super(device);
-    init_(width, height);
-    init_();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = cast(NSAutoreleasePool) (new NSAutoreleasePool()).alloc().init();
+    try {
+        init_(width, height);
+        init_();
+    } finally {
+        if (pool !is null) pool.release();
+    }
 }
 
 /**
@@ -200,11 +211,11 @@
  * provided image, with an appearance that varies depending
  * on the value of the flag. The possible flag values are:
  * <dl>
- * <dt><b>IMAGE_COPY</b></dt>
+ * <dt><b>{@link DWT#IMAGE_COPY}</b></dt>
  * <dd>the result is an identical copy of srcImage</dd>
- * <dt><b>IMAGE_DISABLE</b></dt>
+ * <dt><b>{@link DWT#IMAGE_DISABLE}</b></dt>
  * <dd>the result is a copy of srcImage which has a <em>disabled</em> look</dd>
- * <dt><b>IMAGE_GRAY</b></dt>
+ * <dt><b>{@link DWT#IMAGE_GRAY}</b></dt>
  * <dd>the result is a copy of srcImage which has a <em>gray scale</em> look</dd>
  * </dl>
  *
@@ -238,37 +249,40 @@
         default:
             DWT.error(DWT.ERROR_INVALID_ARGUMENT);
     }
-    device = this.device;
-    this.type = srcImage.type;
 
-    /* Get source image size */
-    NSSize size = srcImage.handle.size();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        device = this.device;
+        this.type = srcImage.type;
+        /* Get source image size */
+        NSSize size = srcImage.handle.size();
     int width = cast(int)size.width;
     int height = cast(int)size.height;
-    NSBitmapImageRep srcRep = srcImage.imageRep;
+        NSBitmapImageRep srcRep = srcImage.imageRep;
     NSInteger bpr = srcRep.bytesPerRow();
 
-    /* Copy transparent pixel and alpha data when necessary */
-    transparentPixel = srcImage.transparentPixel;
-    alpha = srcImage.alpha;
-    if (srcImage.alphaData !is null) {
-        alphaData = new byte[srcImage.alphaData.length];
-        System.arraycopy(srcImage.alphaData, 0, alphaData, 0, alphaData.length);
-    }
+        /* Copy transparent pixel and alpha data when necessary */
+        transparentPixel = srcImage.transparentPixel;
+        alpha = srcImage.alpha;
+        if (srcImage.alphaData !is null) {
+            alphaData = new byte[srcImage.alphaData.length];
+            System.arraycopy(srcImage.alphaData, 0, alphaData, 0, alphaData.length);
+        }
 
-    /* Create the image */
+        /* Create the image */
     handle = cast(NSImage)(new NSImage()).alloc();
-    handle = handle.initWithSize(size);
+        handle = handle.initWithSize(size);
     NSBitmapImageRep rep = imageRep = cast(NSBitmapImageRep)(new NSBitmapImageRep()).alloc();
-    rep = rep.initWithBitmapDataPlanes_pixelsWide_pixelsHigh_bitsPerSample_samplesPerPixel_hasAlpha_isPlanar_colorSpaceName_bitmapFormat_bytesPerRow_bitsPerPixel_(null, cast(NSInteger) width, cast(NSInteger) height, srcRep.bitsPerSample(), srcRep.samplesPerPixel(), srcRep.samplesPerPixel() is 4, srcRep.isPlanar(), OS.NSDeviceRGBColorSpace, NSAlphaFirstBitmapFormat | NSAlphaNonpremultipliedBitmapFormat, srcRep.bytesPerRow(), srcRep.bitsPerPixel());
-    handle.addRepresentation(rep);
-    
+    rep = rep.initWithBitmapDataPlanes(null, width, height, srcRep.bitsPerSample(), srcRep.samplesPerPixel(), srcRep.samplesPerPixel() is 4, srcRep.isPlanar(), OS.NSDeviceRGBColorSpace, NSAlphaFirstBitmapFormat | NSAlphaNonpremultipliedBitmapFormat, srcRep.bytesPerRow(), srcRep.bitsPerPixel());
+        handle.addRepresentation(rep);
+
     objc.id data = rep.bitmapData();
-    OS.memmove(data, srcImage.imageRep.bitmapData(), cast(size_t) (width * height * 4));
-    if (flag !is DWT.IMAGE_COPY) {
-        
-        /* Apply transformation */
-        switch (flag) {
+    OS.memmove(data, srcImage.imageRep.bitmapData(), width * height * 4);
+        if (flag !is DWT.IMAGE_COPY) {
+
+            /* Apply transformation */
+            switch (flag) {
             case DWT.IMAGE_DISABLE: {
                 Color zeroColor = device.getSystemColor(DWT.COLOR_WIDGET_NORMAL_SHADOW);
                 RGB zeroRGB = zeroColor.getRGB();
@@ -280,7 +294,7 @@
                 byte oneRed = cast(byte)oneRGB.red;
                 byte oneGreen = cast(byte)oneRGB.green;
                 byte oneBlue = cast(byte)oneRGB.blue;
-                byte[] line = new byte[bpr];
+                byte[] line = new byte[(int)/*64*/bpr];
                 for (int y=0; y<height; y++) {
                     OS.memmove(line.ptr, data + (y * bpr), bpr);
                     int offset = 0;
@@ -305,7 +319,7 @@
                 break;
             }
             case DWT.IMAGE_GRAY: {          
-                byte[] line = new byte[bpr];
+                byte[] line = new byte[(int)/*64*/bpr];
                 for (int y=0; y<height; y++) {
                     OS.memmove(line.ptr, data + (y * bpr), bpr);
                     int offset = 0;
@@ -321,9 +335,12 @@
                 }
                 break;
             }
+            }
         }
+    init_();
+    } finally {
+        if (pool !is null) pool.release();
     }
-    init_();
 }
 
 /**
@@ -359,8 +376,14 @@
 public this(Device device, Rectangle bounds) {
     super(device);
     if (bounds is null) DWT.error(DWT.ERROR_NULL_ARGUMENT);
-    init_(bounds.width, bounds.height);
-    init_();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        init_(bounds.width, bounds.height);
+        init_();
+    } finally {
+        if (pool !is null) pool.release();
+    }
 }
 
 /**
@@ -383,8 +406,14 @@
  */
 public this(Device device, ImageData data) {
     super(device);
-    init_(data);
-    init_();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        init_(data);
+        init_();
+    } finally {
+        if (pool !is null) pool.release();
+    }
 }
 
 /**
@@ -419,11 +448,17 @@
     if (source.width !is mask.width || source.height !is mask.height) {
         DWT.error(DWT.ERROR_INVALID_ARGUMENT);
     }
-    mask = ImageData.convertMask(mask);
-    ImageData image = new ImageData(source.width, source.height, source.depth, source.palette, source.scanlinePad, source.data);
-    image.maskPad = mask.scanlinePad;
-    image.maskData = mask.data;
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        mask = ImageData.convertMask(mask);
+        ImageData image = new ImageData(source.width, source.height, source.depth, source.palette, source.scanlinePad, source.data);
+        image.maskPad = mask.scanlinePad;
+        image.maskData = mask.data;
     init_(image);
+    } finally {
+        if (pool !is null) pool.release();
+    }
 }
 
 /**
@@ -476,8 +511,14 @@
  */
 public this(Device device, InputStream stream) {
     super(device);
-    init_(new ImageData(stream));
-    init_();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = cast(NSAutoreleasePool) (new NSAutoreleasePool()).alloc().init();
+    try {
+        init_(new ImageData(stream));
+        init_();
+    } finally {
+        if (pool !is null) pool.release();
+    }
 }
 
 /**
@@ -509,40 +550,52 @@
  */
 public this(Device device, String filename) {
     super(device);
-    init_(new ImageData(filename));
-    init_();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = cast(NSAutoreleasePool) (new NSAutoreleasePool()).alloc().init();
+    try {
+        init_(new ImageData(filename));
+        init_();
+    } finally {
+        if (pool !is null) pool.release();
+    }
 }
 
 void createAlpha () {
     if (transparentPixel is -1 && alpha is -1 && alphaData is null) return;
-    NSSize size = handle.size();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        NSSize size = handle.size();
     int height = cast(int)size.height;
     NSInteger bpr = imageRep.bytesPerRow();
     size_t dataSize = height * bpr;
-    byte[] srcData = new byte[dataSize];
+        byte[] srcData = new byte[dataSize];
     OS.memmove(srcData.ptr, imageRep.bitmapData(), dataSize);
-    if (transparentPixel !is -1) {
-        for (int i=0; i<dataSize; i+=4) {
-            int pixel = ((srcData[i+1] & 0xFF) << 16) | ((srcData[i+2] & 0xFF) << 8) | (srcData[i+3] & 0xFF);
+        if (transparentPixel !is -1) {
+            for (int i=0; i<dataSize; i+=4) {
+                int pixel = ((srcData[i+1] & 0xFF) << 16) | ((srcData[i+2] & 0xFF) << 8) | (srcData[i+3] & 0xFF);
             srcData[i] = cast(byte)(pixel is transparentPixel ? 0 : 0xFF); 
-        }
-    } else if (alpha !is -1) {
+            }
+        } else if (alpha !is -1) {
         byte a = cast(byte)this.alpha;
-        for (int i=0; i<dataSize; i+=4) {
-            srcData[i] = a;             
-        }
-    } else {
+            for (int i=0; i<dataSize; i+=4) {
+                srcData[i] = a;             
+            }
+        } else {
         int width = cast(int)size.width;
-        int offset = 0, alphaOffset = 0;
-        for (int y = 0; y<height; y++) {
-            for (int x = 0; x<width; x++) {
-                srcData[offset] = alphaData[alphaOffset];
-                offset += 4;
-                alphaOffset += 1;
+            int offset = 0, alphaOffset = 0;
+            for (int y = 0; y<height; y++) {
+                for (int x = 0; x<width; x++) {
+                    srcData[offset] = alphaData[alphaOffset];
+                    offset += 4;
+                    alphaOffset += 1;
+                }
             }
         }
+    OS.memmove(imageRep.bitmapData(), srcData.ptr, dataSize);
+    } finally {
+        if (pool !is null) pool.release();
     }
-    OS.memmove(imageRep.bitmapData(), srcData.ptr, dataSize);
 }
 
 void destroy() {
@@ -615,11 +668,17 @@
  */
 public Rectangle getBounds() {
     if (isDisposed()) DWT.error(DWT.ERROR_GRAPHIC_DISPOSED);
-    if (width !is -1 && height !is -1) {
-        return new Rectangle(0, 0, width, height);
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        if (width !is -1 && height !is -1) {
+            return new Rectangle(0, 0, width, height);
+        }
+        NSSize size = handle.size();
+    return new Rectangle(0, 0, width = cast(int)size.width, height = cast(int)size.height);
+    } finally {
+        if (pool !is null) pool.release();
     }
-    NSSize size = handle.size();
-    return new Rectangle(0, 0, width = cast(int)size.width, height = cast(int)size.height);
 }
 
 /**
@@ -638,52 +697,56 @@
  */
 public ImageData getImageData() {
     if (isDisposed()) DWT.error(DWT.ERROR_GRAPHIC_DISPOSED);
-
-    NSSize size = handle.size();
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        NSSize size = handle.size();
     int width = cast(int)size.width;
     int height = cast(int)size.height;
-    NSBitmapImageRep imageRep = this.imageRep;
+        NSBitmapImageRep imageRep = this.imageRep;
     NSInteger  bpr = imageRep.bytesPerRow();
     NSInteger  bpp = imageRep.bitsPerPixel();
     size_t dataSize = height * bpr;
-    byte[] srcData = new byte[dataSize];
+        byte[] srcData = new byte[dataSize];
     OS.memmove(srcData.ptr, imageRep.bitmapData(), dataSize);
-    
-    PaletteData palette = new PaletteData(0xFF0000, 0xFF00, 0xFF);
-    ImageData data = new ImageData(width, height, bpp, palette);
-    data.data = srcData;
-    data.bytesPerLine = bpr;
+
+        PaletteData palette = new PaletteData(0xFF0000, 0xFF00, 0xFF);
+        ImageData data = new ImageData(width, height, (int)/*64*/bpp, palette, 4, srcData);
+        data.bytesPerLine = (int)/*64*/bpr;
 
-    data.transparentPixel = transparentPixel;
-    if (transparentPixel is -1 && type is DWT.ICON) {
-        /* Get the icon mask data */
-        int maskPad = 2;
-        int maskBpl = (((width + 7) / 8) + (maskPad - 1)) / maskPad * maskPad;
-        byte[] maskData = new byte[height * maskBpl];
-        int offset = 0, maskOffset = 0;
-        for (int y = 0; y<height; y++) {
-            for (int x = 0; x<width; x++) {
-                if (srcData[offset] !is 0) {
-                    maskData[maskOffset + (x >> 3)] |= (1 << (7 - (x & 0x7)));
-                } else {
-                    maskData[maskOffset + (x >> 3)] &= ~(1 << (7 - (x & 0x7)));
+        data.transparentPixel = transparentPixel;
+        if (transparentPixel is -1 && type is DWT.ICON) {
+            /* Get the icon mask data */
+            int maskPad = 2;
+            int maskBpl = (((width + 7) / 8) + (maskPad - 1)) / maskPad * maskPad;
+            byte[] maskData = new byte[height * maskBpl];
+            int offset = 0, maskOffset = 0;
+            for (int y = 0; y<height; y++) {
+                for (int x = 0; x<width; x++) {
+                    if (srcData[offset] !is 0) {
+                        maskData[maskOffset + (x >> 3)] |= (1 << (7 - (x & 0x7)));
+                    } else {
+                        maskData[maskOffset + (x >> 3)] &= ~(1 << (7 - (x & 0x7)));
+                    }
+                    offset += 4;
                 }
-                offset += 4;
+                maskOffset += maskBpl;
             }
-            maskOffset += maskBpl;
+            data.maskData = maskData;
+            data.maskPad = maskPad;
+        }
+        for (int i = 0; i < srcData.length; i+= 4) {
+            srcData[i] = 0;
         }
-        data.maskData = maskData;
-        data.maskPad = maskPad;
+        data.alpha = alpha;
+        if (alpha is -1 && alphaData !is null) {
+            data.alphaData = new byte[alphaData.length];
+            System.arraycopy(alphaData, 0, data.alphaData, 0, alphaData.length);
+        }
+        return data;
+    } finally {
+        if (pool !is null) pool.release();
     }
-    for (int i = 0; i < srcData.length; i+= 4) {
-        srcData[i] = 0;
-    }
-    data.alpha = alpha;
-    if (alpha is -1 && alphaData !is null) {
-        data.alphaData = new byte[alphaData.length];
-        System.arraycopy(alphaData, 0, data.alphaData, 0, alphaData.length);
-    }
-    return data;
 }
 
 /**  
@@ -707,11 +770,18 @@
     Image image = new Image(device);
     image.type = type;
     image.handle = nsImage;
-    NSImageRep rep = nsImage.bestRepresentationForDevice(null);
-    if (rep.isKindOfClass(NSBitmapImageRep.static_class())) { 
-        image.imageRep = new NSBitmapImageRep(rep.id_);
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        NSImageRep rep = nsImage.bestRepresentationForDevice(null);
+        if (rep.isKindOfClass(OS.class_NSBitmapImageRep)) { 
+            rep.retain();
+            image.imageRep = new NSBitmapImageRep(rep.id_);
+        }
+        return image;
+    } finally {
+        if (pool !is null) pool.release();
     }
-    return image;
 }
 
 /**
@@ -744,7 +814,7 @@
     size.height = height;
     handle = handle.initWithSize(size);
     NSBitmapImageRep rep = imageRep = cast(NSBitmapImageRep)(new NSBitmapImageRep()).alloc();
-    rep = rep.initWithBitmapDataPlanes_pixelsWide_pixelsHigh_bitsPerSample_samplesPerPixel_hasAlpha_isPlanar_colorSpaceName_bitmapFormat_bytesPerRow_bitsPerPixel_(null, cast(NSInteger) width, cast(NSInteger) height, 8, 3, false, false, OS.NSDeviceRGBColorSpace, NSAlphaFirstBitmapFormat | NSAlphaNonpremultipliedBitmapFormat, cast(NSInteger) (width * 4), 32);
+    rep = rep.initWithBitmapDataPlanes_(null, width, height, 8, 3, false, false, OS.NSDeviceRGBColorSpace, NSAlphaFirstBitmapFormat | NSAlphaNonpremultipliedBitmapFormat, width * 4, 32);
     OS.memset(rep.bitmapData(), 0xFF, cast(size_t) (width * height * 4));
     handle.addRepresentation(rep);
 //  rep.release();
@@ -853,8 +923,7 @@
     size.height = height;
     handle = handle.initWithSize(size);
     NSBitmapImageRep rep = imageRep = cast(NSBitmapImageRep)(new NSBitmapImageRep()).alloc();
-    rep = rep.initWithBitmapDataPlanes_pixelsWide_pixelsHigh_bitsPerSample_samplesPerPixel_hasAlpha_isPlanar_colorSpaceName_bitmapFormat_bytesPerRow_bitsPerPixel_(
-            null, cast(NSInteger) width, cast(NSInteger) height, 8, hasAlpha ? 4 : 3, hasAlpha, false, OS.NSDeviceRGBColorSpace, NSAlphaFirstBitmapFormat | NSAlphaNonpremultipliedBitmapFormat, cast(NSInteger) bpr, 32);
+    rep = rep.initWithBitmapDataPlanes(0, width, height, 8, hasAlpha ? 4 : 3, hasAlpha, false, OS.NSDeviceRGBColorSpace, OS.NSAlphaFirstBitmapFormat | OS.NSAlphaNonpremultipliedBitmapFormat, bpr, 32);
     OS.memmove(rep.bitmapData(), buffer.ptr, dataSize); 
     handle.addRepresentation(rep);
 //  rep.release();
@@ -878,39 +947,43 @@
     if (type !is DWT.BITMAP || memGC !is null) {
         DWT.error(DWT.ERROR_INVALID_ARGUMENT);
     }
-    NSGraphicsContext current = NSGraphicsContext.currentContext();
-    NSBitmapImageRep rep = imageRep;
-    if (imageRep.hasAlpha()) {
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
+    try {
+        NSBitmapImageRep rep = imageRep;
+        if (imageRep.hasAlpha()) {
         NSInteger bpr = width * 4;
         rep = cast(NSBitmapImageRep)(new NSBitmapImageRep()).alloc();
         objc.id bitmapData = imageRep.bitmapData();
         if (data.bitmapDataAddress !is null) OS.free(data.bitmapDataAddress);
-        data.bitmapDataAddress = cast(ubyte*) OS.malloc((void*).sizeof);
-        OS.memmove(data.bitmapDataAddress, bitmapData, (void*).sizeof);
-        rep = rep.initWithBitmapDataPlanes_pixelsWide_pixelsHigh_bitsPerSample_samplesPerPixel_hasAlpha_isPlanar_colorSpaceName_bitmapFormat_bytesPerRow_bitsPerPixel_(
-                &data.bitmapDataAddress, cast(NSInteger) width, cast(NSInteger) height, 8, 3, false, false, OS.NSDeviceRGBColorSpace, NSAlphaFirstBitmapFormat , bpr, 32);
-        rep.autorelease();
+        data.bitmapDataAddress = cast(ubyte*) OS.malloc(C.PTR_SIZEOF);
+        OS.memmove(data.bitmapDataAddress, bitmapData, C.PTR_SIZEOF);
+            rep = rep.initWithBitmapDataPlanes(data.bitmapDataAddress, width, height, 8, 3, false, false, OS.NSDeviceRGBColorSpace, OS.NSAlphaFirstBitmapFormat , bpr, 32);
+            rep.autorelease();
+        }
+        handle.setCacheMode(OS.NSImageCacheNever);
+        NSGraphicsContext context = NSGraphicsContext.graphicsContextWithBitmapImageRep(rep);
+        NSGraphicsContext.setCurrentContext(context);
+        NSAffineTransform transform = NSAffineTransform.transform();
+        NSSize size = handle.size();
+        transform.translateXBy(0, size.height);
+        transform.scaleXBy(1, -1);
+        transform.set();
+        if (data !is null) {
+            int mask = DWT.LEFT_TO_RIGHT | DWT.RIGHT_TO_LEFT;
+            if ((data.style & mask) is 0) {
+                data.style |= DWT.LEFT_TO_RIGHT;
+            }
+            data.device = device;
+            data.background = device.COLOR_WHITE.handle;
+            data.foreground = device.COLOR_BLACK.handle;
+            data.font = device.systemFont;
+            data.image = this;
+        }
+    return context.id_;
+    } finally {
+        if (pool !is null) pool.release();
     }
-    NSGraphicsContext context = NSGraphicsContext.graphicsContextWithBitmapImageRep(rep);
-    NSGraphicsContext.setCurrentContext(context);
-    NSAffineTransform transform = NSAffineTransform.transform();
-    NSSize size = handle.size();
-    transform.translateXBy(0, size.height);
-    transform.scaleXBy(1, -1);
-    transform.set();
-    if (data !is null) {
-        int mask = DWT.LEFT_TO_RIGHT | DWT.RIGHT_TO_LEFT;
-        if ((data.style & mask) is 0) {
-            data.style |= DWT.LEFT_TO_RIGHT;
-        }
-        data.device = device;
-        data.background = device.COLOR_WHITE.handle;
-        data.foreground = device.COLOR_BLACK.handle;
-        data.font = device.systemFont;
-        data.image = this;
-    }
-    NSGraphicsContext.setCurrentContext(current);
-    return context.id_;
 }
 
 /**  
@@ -927,8 +1000,15 @@
  * @param data the platform specific GC data 
  */
 public void internal_dispose_GC (objc.id context, GCData data) {
-    if (data.bitmapDataAddress !is null) OS.free(data.bitmapDataAddress);
-    data.bitmapDataAddress = null;
+    NSAutoreleasePool pool = null;
+    if (!NSThread.isMainThread()) pool = cast(NSAutoreleasePool) (new NSAutoreleasePool()).alloc().init();
+    try {
+        if (data.bitmapDataAddress !is null) OS.free(data.bitmapDataAddress);
+        data.bitmapDataAddress = null;
+//      handle.setCacheMode(OS.NSImageCacheDefault);
+    } finally {
+        if (pool !is null) pool.release();
+    }
 }
 
 /**