作为Android开发者,虽然不是大牛,但也接触了很多图片加载框架,因为手机上最难处理最占内存的往往也就是图片,如果图片处理不好,很容易引起程序崩溃。到目前为止我接触过很多种图片加载框架,其中主要有:UniversalImageLoader,Picasso,Glide,Fresco。
Fresco是Facebook最新推出的一款用于Android应用中展示图片的强大图片库,可以从网络、本地存储和本地资源中加载图片。其中的Drawees可以显示占位符,直到图片加载完成。而当图片从屏幕上消失时,会自动释放内存。由于目前项目中使用到了Fresco,所以针对Fresco做一下源码分析。
1.功能介绍
Fresco类似ImageLoader和Picasoo一样,操作起来都比较简单,几行代码就可以开始使用了。可以简单的在xml里使用SimpleDraweeView配置一些属性。在代码中使用SimpleDraweeView的setImageURI方法来进行图片的加载。
Fresco有很大的优点,Fresco的中文文档中说的就很明白,主要优点有:
Fresco总体上也是MVC模式,但是其中包含了很多的设计模式,之后会慢慢叙述。在源代码中。
- DraweeView就相当于View层,负责图片展示以及各种loading,加载效果。
- DraweeController负责接洽View层的展示,每一个view会有一个mDraweeHolder,holder将view中的各种除了展示的操作解耦出来,分而治之。holder中又包含一个controller。controller则负责与下一层hierarchy的连接操作。
- DraweeHierarchy相当于M层,用于下载和转换等,维护最终绘制和呈现的Drawable对象。
3.Fresco简单使用
使用起来很简单,在Android Studio里面的build.gradle文件中配置好对fresco的引用。
dependencies {
compile 'com.facebook.fresco:fresco:0.3.0+'
}
之后要在Application类中进行初始化操作:
Fresco.initialize(this, FrescoConfig.getImagePipelineConfig(this));
FrescoConfig中可以设置一些缓存空间大小,缓存图片地址,以及设置几级缓存。MemoryCacheParams可以对内存进行配置:
//内存配置
final MemoryCacheParams bitmapCacheParams = new MemoryCacheParams(
FrescoConfig.MAX_MEMORY_CACHE_SIZE, // 内存缓存中总图片的最大大小,以字节为单位。
Integer.MAX_VALUE, // 内存缓存中图片的最大数量。
FrescoConfig.MAX_MEMORY_CACHE_SIZE, // 内存缓存中准备清除但尚未被删除的总图片的最大大小,以字节为单位。
Integer.MAX_VALUE, // 内存缓存中准备清除的总图片的最大数量。
Integer.MAX_VALUE); // 内存缓存中单个图片的最大大小。
要想使用刚才设置的内存缓存配置需要,使用得到一个Supplier才能设置成功。
//修改内存图片缓存数量,空间策略(这个方式有点恶心)
Supplier<MemoryCacheParams> mSupplierMemoryCacheParams = new Supplier<MemoryCacheParams>() {
@Override
public MemoryCacheParams get() {
return bitmapCacheParams;
}
};
还可以对小图片和默认图片进行磁盘的配置:
public static final String IMAGE_PIPELINE_CACHE_DIR = "/rodriguez/image";//默认图所放路径的文件夹名
public static final int MAX_DISK_CACHE_VERYLOW_SIZE = 10 * ByteConstants.MB;//默认图极低磁盘空间缓存的最大值
public static final int MAX_DISK_CACHE_LOW_SIZE = 30 * ByteConstants.MB;//默认图低磁盘空间缓存的最大值
public static final int MAX_DISK_CACHE_SIZE = 50 * ByteConstants.MB;//默认图磁盘缓存的最大值
//默认图片的磁盘配置
DiskCacheConfig diskCacheConfig = DiskCacheConfig.newBuilder()
.setBaseDirectoryPath(Environment.getExternalStorageDirectory().getAbsoluteFile())//缓存图片基路径
.setBaseDirectoryName(IMAGE_PIPELINE_CACHE_DIR)//文件夹名
// .setCacheErrorLogger(cacheErrorLogger)//日志记录器用于日志错误的缓存。
// .setCacheEventListener(cacheEventListener)//缓存事件侦听器。
// .setDiskTrimmableRegistry(diskTrimmableRegistry)//类将包含一个注册表的缓存减少磁盘空间的环境。
.setMaxCacheSize(FrescoConfig.MAX_DISK_CACHE_SIZE)//默认缓存的最大大小。
.setMaxCacheSizeOnLowDiskSpace(MAX_DISK_CACHE_LOW_SIZE)//缓存的最大大小,使用设备时低磁盘空间。
.setMaxCacheSizeOnVeryLowDiskSpace(MAX_DISK_CACHE_VERYLOW_SIZE)//缓存的最大大小,当设备极低磁盘空间
// .setVersion(version)
.build();
最后一步便是将之前设置的config应用到Fresco中。需要使用到ImagePipelineConfig.Builder,builder中可以对很多属性进行配置,比如图片解码库,是否旋转图片,是否渐进式加载等等。需要的同学可以去官方文档中查询相关设置。
//缓存图片配置
ImagePipelineConfig.Builder configBuilder = ImagePipelineConfig.newBuilder(context)
.setBitmapMemoryCacheParamsSupplier(mSupplierMemoryCacheParams)//内存缓存配置(一级缓存,已解码的图片)
.setMainDiskCacheConfig(diskCacheConfig)//磁盘缓存配置(总,三级缓存)
.setSmallImageDiskCacheConfig(diskSmallCacheConfig)//磁盘缓存配置(小图片,可选~三级缓存的小图优化缓存)
;
然后将得到的builder设置到之前的initialize代码中,便可以应用。经过这番操作,初始化配置过程基本上算已经完成。
要使用Fresco加载图片。也是特别简单的。在xml文件中添加上相应的view,在设置一些需要的fresco参数。
<com.facebook.drawee.view.SimpleDraweeView
xmlns:fresco="http://schemas.android.com/apk/res-auto"
android:id="@+id/goods_image"
android:layout_width="match_parent"
android:layout_height="wrap_content"
fresco:progressBarImage="@drawable/loading_circle_gray"
fresco:progressBarAutoRotateInterval="@integer/default_loading_duration"
fresco:failureImage="@drawable/image_default_bg"/>
记住一定要在当前view或者根view中添加xmlns:fresco…这句。当前代码中也只是简单的对loading view和错误图片做了设置。
之后便是最简单也最需要的加载图片了。
imageView.setImageURI(imgUri);
一句话就可以将操作交给Fresco,自己就可以做其他的事情了。