任何图像格式的java图像压缩(jpg,PNG,gif)

我使用下面给出的代码来进行jpeg图像的图像压缩。

File input = new File("digital_image_processing.jpg"); BufferedImage image = ImageIO.read(input); File compressedImageFile = new File("compress.jpg"); OutputStream os = new FileOutputStream(compressedImageFile); Iteratorwriters = ImageIO.getImageWritersByFormatName("jpg"); ImageWriter writer = (ImageWriter) writers.next(); ImageOutputStream ios = ImageIO.createImageOutputStream(os); writer.setOutput(ios); ImageWriteParam param = writer.getDefaultWriteParam(); param.setCompressionMode(ImageWriteParam.MODE_EXPLICIT); param.setCompressionQuality(0.05f); writer.write(null, new IIOImage(image, null, null), param); 

但是当我通过改变ImageIO.getImageWritersByFormatName(“png”)来尝试PNG格式时; 它给我一个不支持压缩的错误。

那么我应该如何修改上面的代码,以支持所有的图像格式压缩

代码的问题在于您使用了ImageWriter.getDefaultWriteParam()。 从ImageWriter.java的以下引用:

public ImageWriteParam getDefaultWriteParam()

返回包含默认值的此文件格式的相应类型的新ImageWriteParam对象,即,如果未指定ImageWriteParam对象,将使用这些值。 这可以作为调整一些参数的起点,也可以单独保留默认设置。

默认实现构造并返回一个新的ImageWriteParam对象,该对象不允许平铺,渐进式编码或压缩,并且将针对当前Locale进行本地化(即,通过调用new ImageWriteParam(getLocale())将获得的内容。

单个插件可以返回ImageWriteParam的实例,并启用其他可选function,或者它们可以返回ImageWriteParam的插件特定子类的实例。

实际行为取决于特定ImageWriteParam的个别实现。 我相信JPG图像工作的原因是JPG的ImageWriteParam为默认的ImageWriteParam设置了canWriteCompressed保护字段,但是对于PNG图像,由于某种原因它不会这样做。

如果你看一下com.sun.imageio.plugins.png.PNGImageWriteParam.java,你会发现它确实没有设置它。

为了使您的代码能够正常工作,您可以这样做:

  File input = new File("digital_image_processing.jpg"); BufferedImage image = ImageIO.read(input); File compressedImageFile = new File("compress.jpg"); OutputStream os = new FileOutputStream(compressedImageFile); Iteratorwriters = ImageIO.getImageWritersByFormatName("jpg"); ImageWriter writer = (ImageWriter) writers.next(); ImageOutputStream ios = ImageIO.createImageOutputStream(os); writer.setOutput(ios); ImageWriteParam param = writer.getDefaultWriteParam(); // Check if canWriteCompressed is true if(param.canWriteCompressed()) { param.setCompressionMode(ImageWriteParam.MODE_EXPLICIT); param.setCompressionQuality(0.05f); } // End of check writer.write(null, new IIOImage(image, null, null), param); 

更新:我试图找到一种方法让您在ImageIO框架内微调PNG图像压缩。 但不幸的是,鉴于目前的实施,似乎几乎不可能。 Java PNG编写器插件具有固定的过滤 – 自适应过滤和固定的deflater级别 – 9这是它可以做的最好的事情。