小问题:由于上传图片太大需要压缩,在使用java的ImageIO类来操作图片的时候,有时候图片生成出来背景失真
原图:
![](https://i-blog.csdnimg.cn/blog_migrate/122896e2d26bb03b00ec780af5ed23cf.jpeg)
失真图片:
![](https://i-blog.csdnimg.cn/blog_migrate/c4cafbc43db5bd79d3617360bb94e758.png)
有三种压缩方式
按指定大小把图片进行缩放(会遵循原图宽高比例)
//按指定大小把图片进行缩和放(会遵循原图高宽比例)
//此处把图片压成400×500的缩略图
Thumbnails.of(fromPic).size(400,500).toFile(toPic);
//变为400*300,遵循原图比例缩或放到400*某个高度
按照指定比列进行缩小和放大
//按照比例进行缩小和放大
Thumbnails.of(fromPic).scale(0.2f).toFile(toPic);//按比例缩小
Thumbnails.of(fromPic).scale(2f);//按比例放大
图片尺寸不变,压缩图片文件大小
//图片尺寸不变,压缩图片文件大小outputQuality实现,参数1为最高质量
Thumbnails.of(fromPic).scale(1f).outputQuality(0.25f).toFile(toPic);
toFile(pic)部分可以使用.asBufferedImager().var输出为图片缓存
.eg:
InputStream inputStream = multipartFile.getInputStream();
BufferedImage image = Thumbnails.of(inputStream).size(w, h).asBufferedImage();
ByteArrayOutputStream os = new ByteArrayOutputStream();
ImageIO.write(image , "jpg", os);
return new ByteArrayInputStream(os.toByteArray());
这里由于使用阿里云传输使用putObject();接收inputStream,所以我们在这里就把[BufferedImage]转换成input流进行传输;
我这里转换的图片是jpg,如果用户上传的是png,就会造成透明图层描述错误,失真,因为png是32位图,jpg为24位图,强制转换会造成透明图层的失真
BufferedImage newBufferedImage = new BufferedImage(bufImg.getWidth(), bufImg.getHeight(), BufferedImage.TYPE_INT_RGB);
newBufferedImage.createGraphics().drawImage(bufImg, 0, 0, Color.WHITE, null);
附上完整方法:
public String uploadImg2Oss(MultipartFile file) {
// if (file.getSize() > 1024 * 1024 * 1024 * 200) {
// return "视频太大";//RestResultGenerator.createErrorResult(ResponseEnum.PHOTO_TOO_MAX);
// }
String originalFilename = file.getOriginalFilename();
String substring = originalFilename.substring(originalFilename.lastIndexOf(".")).toLowerCase();
String name = CodecUtil.createUUID() + substring;
try {
InputStream inputStream = file.getInputStream();
//图片读到内存中
BufferedImage bufImg = ImageIO.read(inputStream);
//压缩代码
//设置初始化压缩率为1
float ratio = 1f;
//设置压缩后图片宽度为80
float width =800f;
//获取原图宽高
float ImgWidth = bufImg.getWidth();
float ImgHeight = bufImg.getHeight();
//根据原图宽度,与压缩宽度重新计算压缩率
// if (ImgWidth > width){
// ratio = width / ImgWidth;
// }
ByteArrayOutputStream bos = new ByteArrayOutputStream();
//按压缩率进行压缩
bufImg = Thumbnails.of(bufImg).scale(ratio).asBufferedImage();
// //按指定大小进行压缩
// bufImg = Thumbnails.of(bufImg).size(800,800).asBufferedImage();
// Todo 这里我转换成了jpg格式,一旦用户传来的是png,就会造成透明图层描述错误,失真,因为png是32位图,jpg为24位图,强制转换会造成透明图层的失真
//设置转换规格,颜色空间,传入图片image中的wh参数
BufferedImage newBufferedImage = new BufferedImage(bufImg.getWidth(), bufImg.getHeight(), BufferedImage.TYPE_INT_RGB);
//使用新图片缓冲流生成图片
newBufferedImage.createGraphics().drawImage(bufImg, 0, 0, Color.WHITE, null);
//先转成jpg压缩,然后通过oss来修改为源文件本来的后缀格式
ImageIO.write(newBufferedImage,"jpg",bos);
//获取输出流
inputStream = new ByteArrayInputStream(bos.toByteArray());
this.uploadFile2OSS(inputStream, name);
return name;//RestResultGenerator.createSuccessResult(name);
} catch (Exception e) {
return "上传失败";//RestResultGenerator.createErrorResult(ResponseEnum.PHOTO_UPLOAD);
}
}