关于Bitmap位图压缩图片的三种方式

2016-08-27 23:45 评论 0 条

摘要

对图片进行压缩,为了防止OutOfMemory(OOM),出现OOM的其中一种情况是对图片进行质量压缩时,调用的是Bitmap的compress(Bitmap.CompressFormat format, int quality, OutputStream stream),传递三个参数,format指定Bitmap压缩的格式:PNG,JPEG,WEBP,例如:Bitmap.CompressFormat.JPEG;第二个参数,quality指定压缩的质量,质量参数取值0——100,越接近0,压缩越厉害,像素减少,失真严重;第三个参数字节输出流对象,通常使用ByteArrayOutputStream字节数组输出流,缓冲字节数组,最后将字节数组缓冲流中的字节数重新生成转换成Bitmap对象,即压缩后的对象,例如:

  1. ByteArrayOutputStream baos = new ByteArrayOutputStream();  
  2.     image.compress(Bitmap.CompressFormat.JPEG, 100, baos);  
  3.     while (baos.toByteArray().length / 1024 > 1024) {// 判断如果图片大于1M,进行压缩避免在生成图片(BitmapFactory.decodeStream)时溢出  
  4.         baos.reset();// 重置baos即清空baos  
  5.         image.compress(Bitmap.CompressFormat.JPEG, 50, baos);// 这里压缩50%,把压缩后的数据存放到baos中  
  6.     }  
  7.     ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());  
  8.     BitmapFactory.Options newOpts = new BitmapFactory.Options();  
  9.     // 开始读入图片,此时把options.inJustDecodeBounds 设回true了  
  10.     newOpts.inJustDecodeBounds = true;  
  11.     Bitmap bitmap = BitmapFactory.decodeStream(isBm, null, newOpts);  

一.Bitmap类使用总结

Bitmap位于android.graphics包下,从上面压缩的例子中可以看出,Bitmap俗称位图,将图片转换成Bitmap对象,可以获取图片的高度/宽度/密度/字节数等信息,同理也可以设置图片的高度/宽度/密度/字节数等,这就稍微说明了Bitmap类适合处理图片压缩。下面继续看如何对图片进行比例压缩,压缩图片的比例为:480x800

  1. /**按照缩放比压缩图片 
  2.  * @param image 
  3.  * @return 
  4.  */  
  5. public static Bitmap comp(Bitmap image) {  
  6.     ByteArrayOutputStream baos = new ByteArrayOutputStream();  
  7.     image.compress(Bitmap.CompressFormat.JPEG, 1024, baos);  
  8.     while (baos.toByteArray().length / 1024 > 100) {// 判断如果图片大于1M,进行压缩避免在生成图片(BitmapFactory.decodeStream)时溢出  
  9.         baos.reset();// 重置baos即清空baos  
  10.         image.compress(Bitmap.CompressFormat.JPEG, 50, baos);// 这里压缩50%,把压缩后的数据存放到baos中  
  11.     }  
  12.     ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());  
  13.     BitmapFactory.Options newOpts = new BitmapFactory.Options();  
  14.     // 开始读入图片,此时把options.inJustDecodeBounds 设回true了  
  15.     newOpts.inJustDecodeBounds = true;  
  16.     Bitmap bitmap = BitmapFactory.decodeStream(isBm, null, newOpts);  
  17.     newOpts.inJustDecodeBounds = false;  
  18.     int w = newOpts.outWidth;  
  19.     int h = newOpts.outHeight;  
  20.     // 现在主流手机比较多是800*480分辨率,所以高和宽我们设置为  
  21.     float hh = 800f;// 这里设置高度为800f  
  22.     float ww = 480f;// 这里设置宽度为480f  
  23.     // 缩放比。由于是固定比例缩放,只用高或者宽其中一个数据进行计算即可  
  24.     int be = 1;// be=1表示不缩放  
  25.     if (w > h && w > ww) {// 如果宽度大的话根据宽度固定大小缩放  
  26.         be = (int) (newOpts.outWidth / ww);  
  27.     } else if (w < h && h > hh) {// 如果高度高的话根据宽度固定大小缩放  
  28.         be = (int) (newOpts.outHeight / hh);  
  29.     }  
  30.     if (be <= 0)  
  31.         be = 1;  
  32.     newOpts.inSampleSize = be;// 设置缩放比例  
  33.     // 重新读入图片,注意此时已经把options.inJustDecodeBounds 设回false了  
  34.     isBm = new ByteArrayInputStream(baos.toByteArray());  
  35.     bitmap = BitmapFactory.decodeStream(isBm, null, newOpts);  
  36. /       Bitmap b=compressImage(bitmap);// 压缩好比例大小后再进行质量压缩;  
  37.     return bitmap;  
  38. }  

压缩图片,除了压缩图片的质量,压缩的比例,还可以压缩图片的大小,上述代码while循环对图片的大小进行压缩,最终图片字节数小于等于100kb,防止图片OOM Exception。

当前文章价值4.16元,扫一扫支付后添加微信提供帮助!(如不能解决您的问题,可以申请退款)

你可能感兴趣的文章

来源:每日教程每日一例,深入学习实用技术教程,关注公众号TeachCourse
转载请注明出处: https://www.teachcourse.cn/2018.html ,谢谢支持!

资源分享

分类:Android 标签:,
xml命名空间如何为自定义View取名? xml命名空间如何为自定义View取
Android Debug Bridge Android Debug Bridge
Android Studio的调试技能,你懂了吗? Android Studio的调试技能,你
Python库Flask和SQLite数据库创建简单CRUD(创建、读取、更新、删除)应用的示例 Python库Flask和SQLite数据

发表评论

呲牙 憨笑 坏笑 偷笑 色 微笑 抓狂 睡觉 酷 流汗 鼓掌 大哭 可怜 疑问 晕 惊讶 得意 尴尬 发怒 奋斗 衰 骷髅 啤酒 吃饭 礼物 强 弱 握手 OK NO 勾引 拳头 差劲 爱你

表情