【问题标题】:Save a GIF with index transparency using ImageIO out of an image with alpha transparency使用 ImageIO 从具有 alpha 透明度的图像中保存具有索引透明度的 GIF
【发布时间】:2012-01-24 06:43:52
【问题描述】:

我有一个具有 alpha 透明度的 BufferedImage,我需要将其保存为具有索引透明度的 GIF。没有半透明像素,因此应该可以进行转换。

使用http://gman.eichberger.de/2007/07/transparent-gifs-in-java.html 下的代码,我定义了一种透明颜色(例如绿色,它不是当前图像的一部分)并使其透明。效果很好,但它混淆了颜色表,所有颜色看起来都很糟糕(尽管我只使用了 3 种不同的颜色)。

有没有办法调整这个或另一种将这种 ARGB 图像转换为索引图像而不会显着质量损失的方法?

我的图像的构建方式:

BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
Graphics2D graphics = (Graphics2D)image.getGraphics();
graphics.setColor(backgroundColor);
graphics.fillRect(0, 0, width, height);
// Some more painting here
graphics.dispose();

感谢您的帮助!

【问题讨论】:

  • 从 (A)RGB 到索引的颜色转换并非易事,如果您知道您只会使用 3 种颜色,您应该首先将图像创建为索引。如果您需要转换,您应该查看图像库(或自己实现错误扩散之类的算法,但这不是很聪明)。
  • 感谢您的回答!好吧,问题是我还需要从相同的图形中保存一个 PNG(具有 alpha 透明度),我不想渲染它两次(太贵了)。

标签: java transparency gif bufferedimage javax.imageio


【解决方案1】:

使用 ImageIO 处理透明度,尤其是在保存为 GIF 图像时是一场噩梦。 ImageIO 中对不同图像格式的透明度支持是不完整的,甚至是相同的图像格式但不同的变化。

如果你已经有一个二进制透明的 BufferedImage,我有一个颜色量化工具和一个GIF encoder 来将它保存为具有透明度的 GIF。如果图像的实际颜色小于 256,则不会应用量化。否则,颜色将减少到 256 以下,但保留透明色。在量化过程中可以应用抖动,因此生成的图像大小可能比平时大。

下面的截图显示了两张图片:左边的一张是具有 Alpha 通道透明度的原始 PNG 图像,而右边的一张是从同一个 PNG 图像转换而来的透明 GIF 图像。 GIF 图像实际上减少到 128 色,但质量非常好。 (PNG:49K,GIF:17K)

图片来源:http://svg2rlg.googlecode.com/svn-history/r2/trunk/test-suite/png/butterfly.png

【讨论】:

  • 提醒一下:PNG 具有调色板模式,并且像使用 GIF 一样量化它会产生很大的不同。考虑该 PNG 的this version,它看起来相同但重量为 17k,额外的好处是边框看起来不像锯齿状的混乱(与未调整大小的 gif 示例不同)。我量化了 RGB 颜色,但 alpha 通道仍然是满的 - 不仅仅是像 gif 那样的一级透明度。
  • (也;只是为了完整起见 - 原始 SVG 在通过an optimizer 后小于 GIF 和 PNG)。
猜你喜欢
  • 2019-05-18
  • 1970-01-01
  • 2011-05-10
  • 1970-01-01
  • 1970-01-01
  • 2012-08-28
  • 1970-01-01
  • 2010-10-25
  • 1970-01-01
相关资源
最近更新 更多