转自:http://blog.csdn.net/xiaanming/article/details/26810303
相比上一篇来说,这个Universal-Image-Loader太大了。它功能强大,可扩展性好,高度可定制。
特征:
1)多线程下载图片,图片可来源于网络,文件系统,项目文件夹assets及drawable中等。
2)支持随意的配置ImageLoader,例如线程池,图片下载器,内存缓存策略,图片显示选项及其他一些配置。
3)支持图片的内存缓存,文件系统缓存或SD卡缓存。
4)支持图片下载过程的监听。
5)根据ImageView控件大小对Bitmap进行裁剪,减少Bitmap占用过多的内存。
6)较好的控制图片的加载过程,例如暂停图片加载,重新开始加载图片,一般使用ListView,GridView中,滑动过程中暂停加载图片,停止滑动的时候去加载图片。
7)提供在较慢的网络下对图片进行加载。
下载地址:https://github.com/nostra13/Android-Universal-Image-Loader
支持版本:2.0+
1、下载JAR并导入到libs。
2、声明网络权限和访问SD卡权限。
3、新建一个MyApplication继承Application或新建一个Activity继承Activity,在onCreate()中配置ImageLoader的参数,并初始化到代码中。
public class MyApplication extends Application { @Override public void onCreate() { super.onCreate(); //创建默认的ImageLoader配置参数 ImageLoaderConfiguration configuration = ImageLoaderConfiguration .createDefault(this); //Initialize ImageLoader with configuration. ImageLoader.getInstance().init(configuration); } }
DisplayImageOptions对每个显示任务来说是局部的。通过ImageLoader.displayImage()调用。
ImageLoaderConfiguration是图片加载器ImageLoader的配置参数,每个应用设置一个全局的实例即可。上面是创建了一个默认的ImageLoaderConfigurations,当然也可以自己设置ImageLoaderConfigurations。
// DON'T COPY THIS CODE TO YOUR PROJECT! This is just example of ALL options using. // See the sample project how to use ImageLoader correctly. File cacheDir = StorageUtils.getCacheDirectory(context); ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(context) .memoryCacheExtraOptions(480, 800) // default = device screen dimensions .diskCacheExtraOptions(480, 800, null) .taskExecutor(...) .taskExecutorForCachedImages(...) .threadPoolSize(3) // default .threadPriority(Thread.NORM_PRIORITY - 2) // default .tasksProcessingOrder(QueueProcessingType.FIFO) // default .denyCacheImageMultipleSizesInMemory() .memoryCache(new LruMemoryCache(2 * 1024 * 1024)) .memoryCacheSize(2 * 1024 * 1024) .memoryCacheSizePercentage(13) // default .diskCache(new UnlimitedDiscCache(cacheDir)) // default .diskCacheSize(50 * 1024 * 1024) .diskCacheFileCount(100) .diskCacheFileNameGenerator(new HashCodeFileNameGenerator()) // default .imageDownloader(new BaseImageDownloader(context)) // default .imageDecoder(new BaseImageDecoder()) // default .defaultDisplayImageOptions(DisplayImageOptions.createSimple()) // default .writeDebugLogs() .build();4、加载图片
注意:显示图片时最好不要用ImageLoader,而是使用ImageView.setImageResource()
final ImageView mImageView = (ImageView) findViewById(R.id.image); String imageUrl = "https://lh6.googleusercontent.com/-55osAWw3x0Q/URquUtcFr5I/AAAAAAAAAbs/rWlj1RUKrYI/s1024/A%252520Photographer.jpg"; //显示图片的配置 DisplayImageOptions options = new DisplayImageOptions.Builder() .showImageOnLoading(R.drawable.ic_stub) .showImageOnFail(R.drawable.ic_error) .cacheInMemory(true) .cacheOnDisk(true) .bitmapConfig(Bitmap.Config.RGB_565) .build(); ImageLoader.getInstance().displayImage(imageUrl, mImageView, options);图片显示的配置选项中,添加了一个图片加载中ImageView显示的图片,及图片加载出现错误时显示的图片。而且displayImage()会自动根据控件大小和imageScaleType来裁剪图片。修改下MyApplication,开启log打印:
public class MyApplication extends Application { @Override public void onCreate() { super.onCreate(); //创建默认的ImageLoader配置参数 ImageLoaderConfiguration configuration = new ImageLoaderConfiguration.Builder(this) .writeDebugLogs() //打印log信息 .build(); //Initialize ImageLoader with configuration. ImageLoader.getInstance().init(configuration); } }
5、打印log(可有可无)
public class MyApplication extends Application { @Override public void onCreate() { super.onCreate(); //创建默认的ImageLoader配置参数 ImageLoaderConfiguration configuration = new ImageLoaderConfiguration.Builder(this) .writeDebugLogs() //打印log信息 .build(); //Initialize ImageLoader with configuration. ImageLoader.getInstance().init(configuration); } }6、加载图片时,显示图片下载进度。
只需在displayImage()中传入ImageLoadingProgressListener接口就行了。
imageLoader.displayImage(imageUrl, mImageView, options, new SimpleImageLoadingListener(), new ImageLoadingProgressListener() { @Override public void onProgressUpdate(String imageUri, View view, int current, <span style="white-space:pre"> </span>int total) { } });由于displayImage()中带ImageLoadingProgressListener参数的方法都有带ImageLoadingListener参数,所以这里new一个SimpleImageLoadingListener,然后就可在回调方法onProgressUpdate()得到图片的加载进度。
只需将url稍加改动即可,下面是加载文件系统的图片
//显示图片的配置 DisplayImageOptions options = new DisplayImageOptions.Builder() .showImageOnLoading(R.drawable.ic_stub) .showImageOnFail(R.drawable.ic_error) .cacheInMemory(true) .cacheOnDisk(true) .bitmapConfig(Bitmap.Config.RGB_565) .build(); final ImageView mImageView = (ImageView) findViewById(R.id.image); String imagePath = "/mnt/sdcard/image.png"; String imageUrl = Scheme.FILE.wrap(imagePath); // String imageUrl = "http://img.my.csdn.net/uploads/201309/01/1378037235_7476.jpg"; imageLoader.displayImage(imageUrl, mImageView, options);当图片来源于Content Provider,drawable,assets中,使用也非常简单,只需给每个图片源加上Schema包裹起来(Content Provider除外),然后当做图片的url传递到imageLoader中:
//图片来源于Content provider String contentprividerUrl = "content://media/external/audio/albumart/13"; //图片来源于assets String assetsUrl = Scheme.ASSETS.wrap("image.png"); //图片来源于 String drawableUrl = Scheme.DRAWABLE.wrap("R.drawable.image");
当快速滚动时,希望停止加载图片,而在GridView、ListView停止滑动时加载当前界面的图片。这个框架也提供了这个功能,使用起来也简单,它提供了PauseOnScrollListener这个类来控制ListView、GridView滑动过程中停止加载图片:
listView.setOnScrollListener(new PauseOnScrollListener(imageLoader, pauseOnScroll, pauseOnFling)); gridView.setOnScrollListener(new PauseOnScrollListener(imageLoader, pauseOnScroll, pauseOnFling));第一个参数是图片加载对象;第二个是控制是否在滑动过程中加载图片,如果需要暂停传true即可;第三个参数控制猛的滑动界面时图片是否加载。
这个框架产生OOM的概率比较小,并不保证OOM问题永不发生。这个框架对OOM做了简单的crash,保证我们的程序遇到OOM而不被crash掉,但如果我们使用该框架经常发生OOM,该怎么去改善呢?
1、减少线程池中线程的个数。在ImageLoaderConfiguration中的(.threadPoolSize)中配置,推荐1-5。
2、在DisplayImageOptions选项中配置bitmapConfig为Bitmap.Config.RGB_565 ,因为默认是ARGB_8888,使用RGB_565会比ARGB_8888少消耗2倍内存。
3、在ImageLoaderConfiguration中配置图片的内存缓存为memoryCache(new WeakMemoryCache())或者不使用内存缓存。
4、在DisplayImageOptions选项中设置.imageScaleType(ImageScaleType.IN_SAMPLE_INT)或者imageScaleType(ImageScale.EXACTY)
使用这个框架时尽量使用displayImage()去加载图片,loadImage()是将图片对象回调到ImageLoadingListener接口的onLoadingComplete()中,需要手动设置到ImageView上。displayImage()中,对ImageView对象使用的是弱引用,方便垃圾回收器回收ImageView对象,如果我们加载固定大小的图片时,使用loadImage()需要传递一个ImageSize对象,而displayImage()会根据ImageView对象的测量值,或者android:layout_width和android:layout_height设定的值,或者android:maxWidth或android:maxHeight设定的值来裁剪图片。