Java中内置的压缩图片有两种方式:
- 通过Image的getScaledInstance方法将图片尺寸进行压缩,它的压缩策略有:
SCALE_DEFAULT 默认图像缩放算法 SCALE_FAST 缩放速度优先 SCALE_SMOOTH 图像平滑度优先 它的优点是可以在尽量不影响图像质量的情况下对图片进行一定的压缩,缺点是压缩的效果有局限性.
- 使用ImageWriteParam的setCompressionQuality方法设置ImageWrite输出图片时生成的图片质量,它的优点是可以在不改变图片尺寸的情况下将图片的大小压缩,并且压缩效率比较高.
以下代码是将两者一起使用,达到同时控制压缩图片尺寸和大小的功能.
package test; import java.awt.Image; import java.awt.image.BufferedImage; import java.awt.image.ColorModel; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.util.Iterator; import javax.imageio.IIOImage; import javax.imageio.ImageIO; import javax.imageio.ImageTypeSpecifier; import javax.imageio.ImageWriteParam; import javax.imageio.ImageWriter; import javax.imageio.stream.ImageOutputStream; public class CompressPicUtil { public Image CmopressPic(Image image) throws Exception { int newWidth; int newHeight; // 指定生成图宽高 if (image.getWidth(null) > 1024) { //这里可以自己指定缩放的条件 double rate = (double)image.getWidth(null)/1024; newWidth = 1024; newHeight = (int)(image.getHeight(null)/rate); } else { newWidth = image.getWidth(null); newHeight = image.getHeight(null); } // BufferedImage通过缩放进行压缩 压缩策略为Image.SCALE_FAST 速度优先 BufferedImage buffer = new BufferedImage(newWidth, newHeight, BufferedImage.TYPE_INT_BGR); buffer.getGraphics().drawImage(image.getScaledInstance(newWidth, newHeight, Image.SCALE_FAST), 0, 0, null); // 获得一个ImageWriter输出流 ImageWriter writer = null; ImageTypeSpecifier type = ImageTypeSpecifier .createFromRenderedImage(buffer); Iterator iter = ImageIO.getImageWriters(type, "jpg"); if (iter.hasNext()) { writer = (ImageWriter) iter.next(); } if (writer == null) { return null; } IIOImage iioImage = new IIOImage(buffer, null, null); // 指定压缩方式 压缩程度 色彩模式 ImageWriteParam param = writer.getDefaultWriteParam(); param.setCompressionMode(ImageWriteParam.MODE_EXPLICIT); param.setCompressionQuality(0.4F); //这里可以指定压缩的程度 0-1.0 ColorModel colorModel = ColorModel.getRGBdefault(); param.setDestinationType(new javax.imageio.ImageTypeSpecifier(colorModel, colorModel .createCompatibleSampleModel(16, 16))); // 将缓存中的图片按照指定的配置输出到字节数组中 ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); ImageOutputStream outputStream = ImageIO .createImageOutputStream(byteArrayOutputStream); writer.setOutput(outputStream); writer.write(null, iioImage, param); // 从字节数组中读取图片 ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(byteArrayOutputStream.toByteArray()); Image smallImage = ImageIO.read(byteArrayInputStream); return smallImage; } }
它的压缩效果为(压缩时间已经刨去读取文件时间):
文件1 ---- 压缩前大小 3378KB 压缩后大小 44KB 压缩时间 639 ms 图片宽度 1024 图片高度 640
文件2 ---- 压缩前大小 2240KB 压缩后大小 60KB 压缩时间 295 ms 图片宽度 1024 图片高度 640
文件3 ---- 压缩前大小 1161KB 压缩后大小 37KB 压缩时间 224 ms 图片宽度 1024 图片高度 640
文件4 ---- 压缩前大小 1309KB 压缩后大小 50KB 压缩时间 194 ms 图片宽度 1024 图片高度 576
文件5 ---- 压缩前大小 872KB 压缩后大小 26KB 压缩时间 223 ms 图片宽度 1024 图片高度 576
时间: 2024-11-05 22:33:53