美文网首页
BitMapFactory学习积累

BitMapFactory学习积累

作者: liberty_7658 | 来源:发表于2020-09-30 14:39 被阅读0次

为什么会用到这个类?
当我们想将一张图片转换成为bitmap的时候我们就需要用到BitMapFactory方法
当我们想对bimap进行一些调整的时候,需要用到 Bitmap.createBitmap方式来进行调整
关于Bitmap加载,我们离不开类BitmapFactory。
加载文件系统图:BitmapFactory.decodeFile(url)
加载本地资源图:BitmapFactory.decodeResource(resources,R.drawable.**)
加载输入流:BitmapFactory.decodeStream()
加载字节组:BitmapFactory.decodeByteArray()

当加载到比较大的图的时候,会导致内存溢出,这个时候就需要用到Options这个类对图片进行一个压缩处理。实现图片的高效加载。

BitMapFactory.Options:

  • inJustDecodeBounds: 设置为true,则在解码的时候不会返回bitmap,只会返回这个bitmap的尺寸。目的:在只想得到view的尺寸而不需要加载到内存中。
  • inSampleSize:这个值是一个int,当它小于1的时候,将会被当做1处理,如果大于1,那么就会按照比例(1 / inSampleSize)缩小bitmap的宽和高、降低分辨率,大于1时这个值将会被处置为2的倍数。例如,width=100,height=100,inSampleSize=2,那么就会将bitmap处理为,width=50,height=50,宽高降为1 / 2,像素数降为1 / 4。
  • inPreferredConfig:设置色彩模式,默认为ARGB_8888,在这个模式一个像素4bytes空间。对透明度不做要求的话用RGB_565一个像素2bytes。
  • inPremultiplied:这个值和透明度通道到有关,默认为true(返回的bitmap的颜色通道上会预先附加上透明度通道)。
  • inDither:默认为false(不采用抖动解码)
  • inDensity:表示这个bitmap的像素密度(对应的是DisplayMetrix中的densityDpi 不是density)。
  • inTargetDensity:表示要被画出来的目标 像素密度(对应的是DisplayMetrix中的densityDpi 不是density)。
  • inScreenDensity:表示实际设备的像素密度(对应的是DisplayMetrix中的densityDpi 不是density)。
  • inScaled:设置这个bitmap是否可以被缩放。默认为true可以被缩放。
  • inPreferQualityOverSpeed:这个值表示是否在解码时图片有更高的品质,仅用于JPEG格式。如果设置为true,则图片会有更高的品质,但是会解码速度会很慢。
  • outWidth和outHeigh:表示这个Bitmap的宽和高,一般和inJustDecodeBounds一起使用来获得Bitmap的宽高,但是不加载到内存。

压缩方式一:

  • 尺寸压缩:压缩图片的像素【一张图片所占内存大小 = 图片类型(ALPHA_8/ARGB_4444/ARGB_8888/RGB_256) * 宽 * 高】

图片类型:也就是色彩模式

  1. ALPHA_8:每个像素占用1byte内存。
  2. ARGB_4444:每个像素占用2byte内存
  3. ARGB_8888:每个像素占用4byte内存
  4. RGB_565:每个像素占用2byte内存
    而android默认的色彩模式就是ARGB_8888,质量最高,同时内存也是最大。效果也肯定是最好的。

假设一张图1024 1024 模式ARGB_8888 则内存:1024 * 1024 * 4 = 4M

修改图片类型:optins.inPreferredConfig
用这个改变内存大小的三个值得第一个。图片类型,指定为更小的色彩模式,可以让图片的内存变小。

BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig= Bitmap.Config.RGB_565;

修改图片采样率:optins.inSampleSize

options.inPreferredConfig=2;

  • 当inSampleSize=1时,采样后的图片为图片的原始大小。
  • 除了1以外,inSampleSize的取值应该总为2的整数倍,否则会【向下取整】,取一个最接近2的整数倍,比如inSampleSize=3时,系统会取inSampleSize=2
  • 当inSampleSize=2时,采样后的图片的宽高均为原始图片宽高的1/2

假设一张10241024,模式为ARGB_8888的图片,inSampleSize=2,原始占用内存大小是4MB,采样后的图片占用内存大小就是(1024/2) * (1024/2 ) 4 = 1MB

文章引用:
作者:芒果味的你呀
链接:https://www.jianshu.com/p/c77158b6e07e
来源:简书


来自个人使用分析

inDensity 和 inTargetDensity他两一般都是搭配使用的。

在官方解释isDensity里面有这么一句话:
In addition,
* if {@link #inScaled} is set (which it is by default} and this
* density does not match {@link #inTargetDensity}, then the bitmap
* will be scaled to the target density before being returned.
讲的是当设置了isDensity 和 inTargetDensity的时候 如果二者不相等,那么会根据inTargetDensity的值自动进行一个缩放。

例子:

/**
* 设 width = 240  bg:宽480 高:480
* 则:options.inDensity = options.outWidth  //480
*        options.inTargetDensity = widt    //240
*  由于inDensity 和 inTargetDensity 的值不相等 那么我们得到的bitmap的宽度会等于 240 高于也会变成240
*  自动实现了缩放效果。
**/
private fun getAvatar(width: Int, bg: Int): Bitmap {
        val options = BitmapFactory.Options()
        options.inJustDecodeBounds = true
        BitmapFactory.decodeResource(resources, bg, options)
        options.inJustDecodeBounds = false
        options.inDensity = options.outWidth
        options.inTargetDensity = width
        return BitmapFactory.decodeResource(resources, bg, options)
    }

相关文章

网友评论

      本文标题:BitMapFactory学习积累

      本文链接:https://www.haomeiwen.com/subject/bjjuuktx.html