Link to home
Start Free TrialLog in
Avatar of egono
egono

asked on

Create transparent GIF with JAI

Hello,
I'm trying to create a transparent GIF with JAI:

  private static void createImage(BufferedImage argBufferedImage, String argFileName) {
    ImageWriter gifWriter = null;
    IIOImage iioImage = null;
    IIOMetadata iioMetadata = null;

    IIOMetadataNode gifMetadataNode = null;
    IIOMetadataNode tmpNode = null;

    gifWriter = (ImageWriter) ImageIO.getImageWritersByFormatName("gif").next();
    try {
      gifWriter.setOutput(ImageIO.createImageOutputStream(new File(argFileName)));
      iioMetadata = gifWriter.getDefaultImageMetadata(new ImageTypeSpecifier(argBufferedImage), null);
      gifMetadataNode = (IIOMetadataNode) iioMetadata.getAsTree("javax_imageio_gif_image_1.0");
      tmpNode = (IIOMetadataNode) gifMetadataNode.getElementsByTagName("GraphicControlExtension").item(0);
      tmpNode.setAttribute("transparentColorIndex", "0");
      tmpNode.setAttribute("transparentColorFlag", "true");
      iioMetadata.setFromTree("javax_imageio_gif_image_1.0", gifMetadataNode);
      iioImage = new IIOImage(argBufferedImage, null, iioMetadata);
      gifWriter.write(iioImage);
      gifWriter.dispose();
    } catch (Exception e) {
      System.out.println("ex:" + e);
    }
  }

Unfortunately my code doesn't work. Any recommendations?
Avatar of sciuriware
sciuriware

Any error messages?

;JOOP!
Avatar of egono

ASKER

No - the background color is just not set transparent.

I get a

java.lang.NullPointerException
      at com.sun.media.imageioimpl.common.PaletteBuilder.findPaletteEntry(PaletteBuilder.java:349)
      at com.sun.media.imageioimpl.common.PaletteBuilder.getIndexColorModel(PaletteBuilder.java:335)
      at com.sun.media.imageioimpl.common.PaletteBuilder.getIndexedImage(PaletteBuilder.java:184)
      at com.sun.media.imageioimpl.common.PaletteBuilder.createIndexedImage(PaletteBuilder.java:116)
      at com.sun.media.imageioimpl.plugins.gif.GIFImageWriter.write(GIFImageWriter.java:602)
      at com.sun.media.imageioimpl.plugins.gif.GIFImageWriter.write(GIFImageWriter.java:530)
      at javax.imageio.ImageWriter.write(ImageWriter.java:573)

if I want to create a complete transparent gif. But this seems to be a known bug: http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6287936
Again - the NPE is *not* my problem.

regards
Avatar of girionis
Can you try to upgrade/downgrade the library?
Avatar of egono

ASKER

girionis - I could try this, but the environment is given because the jai libs are used for other things too.

the question is: is my code the right way to create a transparent gif?
Not sure tbh. But the exception you get means that something is not loaded up properly so I guess there is a problem either with some sort fo configuration or with the package itself.
Avatar of egono

ASKER

girionis - no the exception is a know bug for complete transparent images, and again this is not my problem.

maybe I should change my question into: How to create a transparent gif with JAI?
This link: http://www.esri.com/software/arcexplorer/about/ae9_faq.html states that this is a limitation. Maybe you can create a transparent PNG and then convert it to GIF?
Avatar of egono

ASKER

some more info. here is how I create my BufferedImage:

        bufferedImage = new BufferedImage(argWidth, argHeight, BufferedImage.TYPE_INT_ARGB);

        graphics2D = bufferedImage.createGraphics();
        if (colorIdx == 0) {
          graphics2D.setBackground(Color.WHITE);
        } else {
          graphics2D.setBackground(Color.BLACK);
        }
        graphics2D.clearRect(0, 0, argWidth, argHeight);
        graphics2D.setColor(Color.BLUE);
        graphics2D.fillRect(0, 0, 10, 10);
Avatar of egono

ASKER

girionis - I'm not displaying the gif with jai, I just want to save it (I'm using Paint.Net to view it)
If you just want to save it just use one of the usual output stream methods that write the binary data on the disk. But I guess the problem is that the image is not what you want and therefore before you save it you need it to be transparent. Not sure how exactly you can do it, but from a quick search on jai-interest archives I found the following URL for GIF files: http://archives.java.sun.com/cgi-bin/wa?A2=ind9902&L=jai-interest&P=R5968&I=-3

You might also want to try this: http://archives.java.sun.com/cgi-bin/wa?S1=jai-interest and do a search for "GIF encoding".
Avatar of egono

ASKER

Now here is a working solution. The trick is to use a IndexColorModel for the image. The createColorModel() method should create the desired color model, in my case a model with just 2 colors (first one is black).

create the image with

[...]
          bufferedImage = new BufferedImage(argWidth, argHeight, BufferedImage.TYPE_BYTE_INDEXED,                                             createColorModel(COLORS[colorIdx]));
[...]


private static IndexColorModel createColorModel(Color argColor) {
    IndexColorModel result = null;
    result = new IndexColorModel(1, 2,
                                 new byte[] {0, (byte)argColor.getRed()},
                                 new byte[] {0, (byte)argColor.getGreen()},
                                 new byte[] {0, (byte)argColor.getBlue()},
                                 0);
    return result;
 }

  private static void createImage(BufferedImage argBufferedImage, String argFileName) {
    ImageWriter gifWriter = null;
    IIOImage iioImage = null;
    IIOMetadata iioMetadata = null;
    gifWriter = (ImageWriter) ImageIO.getImageWritersByFormatName("gif").next();
    try {
      gifWriter.setOutput(ImageIO.createImageOutputStream(new File(argFileName)));
      iioMetadata = gifWriter.getDefaultImageMetadata(new ImageTypeSpecifier(argBufferedImage), null);
      iioImage = new IIOImage(argBufferedImage, null, iioMetadata);
      gifWriter.write(iioImage);
    } catch (Exception e) {
      System.out.println("ex:" + e);
    }

  }


that's it :-)
Fine by me.
ASKER CERTIFIED SOLUTION
Avatar of DarthMod
DarthMod
Flag of United States of America image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial