关于图片加载框架
Posted 庄生晓梦、杨
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了关于图片加载框架相关的知识,希望对你有一定的参考价值。
接上篇,这篇开始对现在比较的流行的第三方图片加载框架做一个对比总结。
这篇文章介绍内容如下:
1、目前流行的图片加载框架有什么?
2、各自的使用方法
3、各自的优缺点
4、优化问题
一、目前流行的图片加载框架有什么?
ImageLoader Glide Picasso Fresso(2015年)
注:由于现在ImageLoader使用较少,本篇博文将不再对它进行阐述。主要以其它三个框架为主,有兴趣的同学可以自行学习。
二、各自的使用方法
Picasso:
Picasso .with(this) .load("图片地址") //转换图片大小 .resize(100,100) //类似于scaleType属性 .centerCrop() //占位图 .placeholder(R.mipmap.ic_launcher) //错误提示图 .error(R.mipmap.ic_launcher) .into(ImageView);
Glide:(使用方法与Picasso基本一致)
Fresco:
<com.facebook.drawee.view.SimpleDraweeView android:id="@+id/my_image_view" android:layout_width="20dp" android:layout_height="20dp" fresco:fadeDuration="300" fresco:actualImageScaleType="focusCrop" fresco:placeholderImage="@color/colorPrimary" fresco:placeholderImageScaleType="fitCenter" fresco:failureImage="@mipmap/ic_launcher" fresco:failureImageScaleType="centerInside" fresco:retryImage="@mipmap/ic_launcher" fresco:retryImageScaleType="centerCrop" fresco:progressBarImage="@mipmap/ic_launcher" fresco:progressBarImageScaleType="centerInside" fresco:progressBarAutoRotateInterval="1000" fresco:backgroundImage="@color/colorPrimary" fresco:overlayImage="@mipmap/ic_launcher" fresco:pressedStateOverlayImage="@color/colorPrimary" fresco:roundAsCircle="false" fresco:roundedCornerRadius="1dp" fresco:roundTopLeft="true" fresco:roundTopRight="false" fresco:roundBottomLeft="false" fresco:roundBottomRight="true" fresco:roundWithOverlayColor="@color/colorPrimary" fresco:roundingBorderWidth="2dp" fresco:roundingBorderColor="@color/colorPrimary" />
fresco属性介绍:
1、必须设置width和Height属性,并且这两个属性不知吹wrap_content,必须强制设置宽高。
2、支持宽高比,通过viewAspectRatio属性指定宽高比,固定宽或高,另一个可以设置为wrap_content
3、placeholderImage及placeholderImageScaleType,设置占位图及占位图的缩放类型
4、roundAsCircle = true设置为圆型图
5、roundedCornerRadius圆角
6、roundWithOverlayColor背景固定成指定的颜色
在使用fresco加载图片时先初始化(推荐在application中初始化)
Fresco.initialize(this);
加载图片只需通过setImageURI就可以实现:
draweeView.setImageURI(uri);
fresco所有属性几乎都支持在代码中进行修改,如果有需要,具体需要方法可以去看官方提供文档,写的很详细。
(注:上面的所有是官方列举出来的,只对部分常用属性作解释。我的demo是在0.12.0版本下运行的,我在做的时候,版本低造成部分属性不支持,注意版本问题哦。
要想让fresco支持webp格式图片,必须引入相关依赖)
三、各自的优缺点
首先说,任何一种框架都不会是绝对完美的,只要是适合你的,就是最好的。所以,选择使用框架的时候,一定要明白它的优缺点,结合你要做的项目进行选择。
Picasso:
优点:
1、Picasso默认加载图片的格式是ARGB_8888,图片清晰度高。
2、在adapter中需要取消已经不在视野范围的ImageView图片资源的加载,否则会导致图片错位,Picasso已经解决了这个问题
3、使用复杂的图片压缩转换来尽可能的减少内存消耗
4、自带内存和硬盘二级缓存功能
缺点:
1、每次缓存的时候,不管imageview的大小是什么,它都会默认缓存整张图片,当显示的时候总是需要调整大小
2、不能加载gif图,加载出来的也是不可以动的
3、圆角图需要自定义转换器,然后通过transform 方法指定,且显示效果不好,或有毛边
Glide:
优点:
1、Picasso的with方法只能传入context对象,而Glide可以传context、Activity、FragmentActivity、Fragment等。
这样做的好处是:可以让图片的加载与Activity或Fragment的声明周期保持一致。在Activity或Fragment销毁的时候停止加载。
2、Glide默认加载的格式是RGB_565,它占用内存仅为ARGB_8888的一半
3、它会根据imageview图片大小不同缓存多张图片,加载速度快,优于Picasso,相当于用空间来换取时间
4、支持gif图(耗内存,慎用)
5、圆角图效果比Picasso好
6、还有一个特性是你可以配置图片显示的动画,而Picasso只有一种动画:fading in。
7、可以使用thumbnail()产生一个你所加载图片的thumbnail。
缺点:
1、加载格式是RGB_565,没有Picasso的图片效果好(但是肉眼并不能分辨,可以选择用这种方法来优化你的项目,减少内存占用)
。。。。
(Picasso和Glide的方法个数分别是840和2678个。必须指出,对于DEX文件65535个方法的限制来说,2678是一个相当大的数字了。建议在使用Glide的时候开启ProGuard。)
总结:Glide和Picasso都不是完美的,从某些方面来说,Glide在图片的缓存上来说是比较不错的,因为它的速度比较快,另外,它
也可以有效的防止OOM错误,而加载gif图片也是Glide的一大优势,但是默认情况下picasso的图片质量是很高的。
另外的一点小建议是,使用Glide的时候把图片的格式改为ARGB8888并且缓存全尺寸和其他尺寸的图片,这样使用可以让加载图片更好。
Fresco
号称是迄今为止安卓最强大的图片加载框架,相对与其它几个框架,他的主要优点就是能够更好的内存管理和更强大的功能。
优点:
1、内存管理,实现了真正意义上的三级缓存,两级内存缓存和一个磁盘缓存。两级内存缓存分别是bitmap缓存和未解码图片的缓存,加快了图片的加载速度。同时值得一提的是,在app切换到后台时,fresco
会自动清理两级的内存缓存,无需手动,
2、支持流式,可以类似网页上模糊渐进式显示图片
3、对多帧动画图片支持的更好,如gif和webp(引导界面的大图用智图压成webp放在drawable中,用fresco加载就可以)
(注:今日对图片加载问题的总结主要是为了webp的引入,它是一种新的图片格式,目前许多网站都有应用,有兴趣的可以继续关注)
缺点:
体积相比其它的框架都大,通常引入后会导致应用的apk增加1.5M到2M
(其实我觉得,相对与fresco的优点,这个缺点不算什么的~当然,如果你的项目仅仅的图片展示,我觉的Glide或Picasso稍微做一些优化也足够了)
四、优化问题
仅提供几种优化方法,根据自己需要进行选择:
1、需要高质量的图片,不满足与Glide的RGB_565
public class GlideConfiguration implements GlideModule { @Override public void applyOptions(Context context, GlideBuilder builder) { // Apply options to the builder here. builder.setDecodeFormat(DecodeFormat.PREFER_ARGB_8888); } @Override public void registerComponents(Context context, Glide glide) { // register ModelLoaders here. } }
然后在AndroidManifest.xml中将GlideModule定义为meta-data
<meta-data android:name="com.inthecheesefactory.lab.glidepicasso.GlideConfiguration" android:value="GlideModule"/>
2、关于Glide
上面提到Glide会缓存不同尺寸图片的大小,当你的页面imageView发生改变时,它会再去请求一张相应尺寸的图片,并进行缓存,加载。这样,根据imageView大小不同,同一张
图片会缓存多次,但是这样加载速度会大大提高,这就是用空间换取时间。而Picasso只会缓存一张全尺寸的,然后根据imageView的大小不同,进行大小调整后进行加载,这样速度就会慢很多。
为避免Glide多次访问网络下载的问题,可以缓存一张全尺寸大图,然后出现不同尺寸的时候,通过调整全尺寸图进行缓存加载。
Glide.with(this) .load("") .diskCacheStrategy(DiskCacheStrategy.ALL) .into();
Picasso通过调整大小进行显示,所以有一些延迟,可以通过设置让其立即显示(效果不明显)
Picasso.noFade();
3、Picasso和Glide都可以配置图片缓存控件的大小!可以根据自己的需要进行适当调整。
最后,推荐一篇关于Picasso源码解析的文章,写的很棒
http://www.jcodecraeer.com/a/anzhuokaifa/androidkaifa/2014/0731/1639.html
以上是关于关于图片加载框架的主要内容,如果未能解决你的问题,请参考以下文章
Android 加载gif图片强大框架(支持预加载缓存,还支持显示静态图片,一行代码全搞定)