Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Drawing on a transparent image using Java SWT

How do I create an in-memory fully transparent SWT image and draw a black line on it with antialias enabled?

I expect the result to include only black color and alpha values ranging from 0 to 255 due to antialias...

I googled and tried everything that I could... is this possible at all?

like image 725
Levente Mészáros Avatar asked Nov 25 '11 14:11

Levente Mészáros


3 Answers

This is how I did and it works:

    Image src = new Image(null, 16, 16);        
    ImageData imageData = src.getImageData();
    imageData.transparentPixel = imageData.getPixel(0, 0);
    src.dispose();
    Image icon = new Image(null, imageData);
    //draw on the icon with gc
like image 73
xihui Avatar answered Nov 15 '22 07:11

xihui


I was able to make this work, although it feels a bit hacky:

Display display = Display.getDefault();

int width = 10;
int height = 10;

Image canvas = new Image(display, width, height);

GC gc = new GC(canvas);

gc.setAntialias(SWT.ON);

// This sets the alpha on the entire canvas to transparent
gc.setAlpha(0);
gc.fillRectangle(0, 0, width, height);

// Reset our alpha and draw a line
gc.setAlpha(255);
gc.setForeground(display.getSystemColor(SWT.COLOR_BLACK));
gc.drawLine(0, 0, width, height);

// We're done with the GC, so dispose of it
gc.dispose();

ImageData canvasData = canvas.getImageData();
canvasData.alphaData = new byte[width * height];

// This is the hacky bit that is making assumptions about
// the underlying ImageData.  In my case it is 32 bit data
// so every 4th byte in the data array is the alpha for that
// pixel...
for (int idx = 0; idx < (width * height); idx++) {
    int coord = (idx * 4) + 3;
    canvasData.alphaData[idx] = canvasData.data[coord];
}

// Now that we've set the alphaData, we can create our
// final image
Image finalImage = new Image(canvasData);

// And get rid of the canvas
canvas.dispose();

After this, finalImage can be drawn into a GC with drawImage and the transparent parts will be respected.

like image 41
Sean Bright Avatar answered Nov 15 '22 07:11

Sean Bright


I made it by allocating an ImageData, making it transparent then creating the Image from the data :

static Image createTransparentImage(Display display, int width, int height) {
    // allocate an image data
    ImageData imData = new ImageData(width, height, 24, new PaletteData(0xff0000,0x00ff00, 0x0000ff));
    imData.setAlpha(0, 0, 0); // just to force alpha array allocation with the right size
    Arrays.fill(imData.alphaData, (byte) 0); // set whole image as transparent

    // Initialize image from transparent image data
    return new Image(display, imData);
}
like image 3
Cédric Avatar answered Nov 15 '22 08:11

Cédric