Android开源框架Universal-Image-Loader学习使用1

一、工作流程:

1、当请求显示图片,调用ImageLoader.displayImage(),首先会

1)计算显示图片的尺寸大小

2)判断该图片是否已存在缓存中,若No,跳到步骤3,若Yes,跳到步骤9

3)判断图片是否已存在本地,若No,跳到步骤4;若Yes,跳到步骤6

4)判断图片允许存储在本地,若No,跳转到步骤6;若Yes,跳到步骤5

5)将图片存储至本地

6)将Image文件decode成Bitmap文件

7)判断是否允许图片存储到缓存中,若No,跳到步骤9;若yes,跳到步骤8

8)将图片存储至缓存中

9)将图片数据从缓存中取出,显示到ImageView控件上

2、每一个图片的加载和显示任务都运行在独立的线程中,除非这个图片缓存在内存中,这种情况下图片会立即显示。如果需要的图片缓存在本地,他们会开启一个独立的线程队列。如果在缓存中没有正确的图片,任务线程会从线程池中获取,因此,快速显示缓存图片时不会有明显的障碍

3、应用环境:

  1. 多线程下载图片,图片可以来源于网络,文件系统,项目文件夹assets中以及drawable中等
  2. 支持随意的配置ImageLoader,例如线程池,图片下载器,内存缓存策略,硬盘缓存策略,图片显示选项以及其他的一些配置
  3. 支持图片的内存缓存,文件系统缓存或者SD卡缓存
  4. 支持图片下载过程的监听
  5. 根据控件(ImageView)的大小对Bitmap进行裁剪,减少Bitmap占用过多的内存
  6. 较好的控制图片的加载过程,例如暂停图片加载,重新开始加载图片,一般使用在ListView,GridView中,滑动过程中暂停加载图片,停止滑动的时候去加载图片
  7. 提供在较慢的网络下对图片进行加载

二、使用教程:

1、设置权限

<uses-permission android:name="android.permission.INTERNET" />

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

2、新建一个Android项目,下载JAR包添加到工程libs目录下

新建一个MyApplication继承Application,并在onCreate()中创建ImageLoader的配置参数,并初始化到ImageLoader中代码如下:

1)使用默认的配置

//创建默认的ImageLoader配置参数

ImageLoaderConfiguration configuration = ImageLoaderConfiguration

.createDefault(this);

//Initialize ImageLoader with configuration.

ImageLoader.getInstance().init(configuration);

2)自己进行配置:

1>定义缓存路径

File cacheDir = StorageUtils.getCacheDirectory(context);

或者自定义缓存路径:

File cacheDir = StorageUtils.getOwnCacheDirectory(getApplicationContext(), "imageloader/Cache");

//这个是你希望的缓存文件的目录:imageloader/Cache

之后在ImageLoaderConfiguration的配置文件中通过设置:

.discCache(new UnlimitedDiscCache(cacheDir))//自定义缓存路径

2>配置

ImageLoaderConfiguration config = new ImageLoaderConfiguration

.Builder(context)

.memoryCacheExtraOptions(480, 800) // max width, max height,即保存的每个缓存文件的最大长宽

.discCacheExtraOptions(480, 800, CompressFormat.JPEG, 75, null) // Can slow ImageLoader, use it carefully (Better don‘t use it)/设置缓存的详细信息,最好不要设置这个

.threadPoolSize(3)//线程池内加载的数量

.threadPriority(Thread.NORM_PRIORITY - 2)

.denyCacheImageMultipleSizesInMemory()

.memoryCache(new UsingFreqLimitedMemoryCache(2 * 1024 * 1024)) // You can pass your own memory cache implementation/你可以通过自己的内存缓存实现

.memoryCacheSize(2 * 1024 * 1024)

.discCacheSize(50 * 1024 * 1024)

.discCacheFileNameGenerator(new Md5FileNameGenerator())//将保存的时候的URI名称用MD5 加密

.tasksProcessingOrder(QueueProcessingType.LIFO)

.discCacheFileCount(100) //缓存的文件数量

.discCache(new UnlimitedDiscCache(cacheDir))//自定义缓存路径

.defaultDisplayImageOptions(DisplayImageOptions.createSimple())

.imageDownloader(new BaseImageDownloader(context, 5 * 1000, 30 * 1000)) // connectTimeout (5 s), readTimeout (30 s)超时时间

.writeDebugLogs() // Remove for release app

.build();//开始构建

// Initialize ImageLoader with configuration.

ImageLoader.getInstance().init(config);//全局初始化此配置

上面的这些就是所有的选项配置,我们在项目中不需要每一个都自己设置,一般使用createDefault()创建的ImageLoaderConfiguration就能使用,然后调用ImageLoader的init()方法将ImageLoaderConfiguration参数传递进去,ImageLoader使用单例模式。

3>在Android Mainfest文件中声明perimisssion及Application

    <manifest>

<uses-permission android:name="android.permission.INTERNET" />

<!-- Include next permission if you want to allow UIL to cache images on SD card -->

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

...

<application android:name="MyApplication">

...

</application>

    </manifest>

3、使用进行加载图片

使用ImageLoader进行图片加载的时候,先要实例化ImageLoader,调用以下方法进行实例化,在每个布局里面都要实例化后再使用。

    protected ImageLoader imageLoader = ImageLoader.getInstance();
(前面配置时有提到)

ImageLoader提供了几个图片加载的方法,主要是这几个displayImage(), loadImage(),loadImageSync(),loadImageSync()

方法是同步的,android4.0有个特性,网络操作不能在主线程,所以loadImageSync()方法我们就不去使用

1>首先用到DisplayImageOptions,可以配置一些图片显示的选项,比如图片在加载中ImageView显示的图片,是否需要使用内存缓存,是否需要使用文件缓存等等,可供我们选择的配置如下:

DisplayImageOptions options;

options = new DisplayImageOptions.Builder()

.showImageOnLoading(R.drawable.ic_launcher) //设置图片在下载期间显示的图片

.showImageForEmptyUri(R.drawable.ic_launcher)//设置图片Uri为空或是错误的时候显示的图片

.showImageOnFail(R.drawable.ic_launcher)  //设置图片加载/解码过程中错误时候显示的图片

.cacheInMemory(true)//设置下载的图片是否缓存在内存中

.cacheOnDisc(true)//设置下载的图片是否缓存在SD卡中

.considerExifParams(true)
 //是否考虑JPEG图像EXIF参数(旋转,翻转)

.imageScaleType(ImageScaleType.EXACTLY_STRETCHED)//设置图片以如何的编码方式显示

.bitmapConfig(Bitmap.Config.RGB_565)//设置图片的解码类型//

.decodingOptions(android.graphics.BitmapFactory.Options decodingOptions)//设置图片的解码配置

//.delayBeforeLoading(int delayInMillis)//int delayInMillis为你设置的下载前的延迟时间

//设置图片加入缓存前,对bitmap进行设置

//.preProcessor(BitmapProcessor preProcessor)

.resetViewBeforeLoading(true)//设置图片在下载前是否重置,复位

.displayer(new RoundedBitmapDisplayer(20))//是否设置为圆角,弧度为多少

.displayer(new FadeInBitmapDisplayer(100))//是否图片加载好后渐入的动画时间

.build();//构建完成

2>先使用ImageLoader的loadImage()方法来加载网络图片

1.使用ImageLoadingListener()的onLoadingComplete的回调方法

final ImageView mImageView = (ImageView) findViewById(R.id.image);

String imageUrl =     "https://lh6.googleusercontent.com/-55osAWw3x0Q/URquUtcFr5I/AAAAAAAAAbs/rWlj1RUKrYI/s1024/A%252520Photographer.jpg";

ImageLoader.getInstance().loadImage(imageUrl, new ImageLoadingListener() {

@Override

public void onLoadingStarted(String imageUri, View view) {

}

@Override

public void onLoadingFailed(String imageUri, View view,

FailReason failReason) {

}

@Override

public void onLoadingComplete(String imageUri, View view, Bitmap loadedImage) {

mImageView.setImageBitmap(loadedImage);

}

@Override

public void onLoadingCancelled(String imageUri, View view) {

}

});

2.由上可看到实际上只使用一个回调方法,可以使用SimpleImageLoadingListener类,该类提供了ImageLoaderListener接口方法的空实现,使用的是缺省适配器模式;

final ImageView mImageView = (ImageView) findViewById(R.id.image);

String imageUrl = "https://lh6.googleusercontent.com/-55osAWw3x0Q/URquUtcFr5I/AAAAAAAAAbs/rWlj1RUKrYI/s1024/A%252520Photographer.jpg";

ImageSize mImageSize = new ImageSize(100, 100);//设置图片大小

//显示图片的配置

DisplayImageOptions options = new DisplayImageOptions.Builder()

.cacheInMemory(true)

.cacheOnDisk(true)

.bitmapConfig(Bitmap.Config.RGB_565)

.build();

ImageLoader.getInstance().loadImage(imageUrl, mImageSize, options, new SimpleImageLoadingListener(){

@Override

public void onLoadingComplete(String imageUri, View view,

Bitmap loadedImage) {

super.onLoadingComplete(imageUri, view, loadedImage);

mImageView.setImageBitmap(loadedImage);

}

});

3>使用displayImage()

displayImage()方法中,对ImageView对象使用的是Weak references,方便垃圾回收器回收ImageView对象,如果我们要加载固定大小的图片的时候,使用loadImage()方法需要传递一个ImageSize对象,而displayImage()方法会根据ImageView对象的测量值,或者android:layout_width
and android:layout_height设定的值,或者android:maxWidth and/or android:maxHeight设定的值来裁剪图片

1.纯粹为了加载默认配置的一个图片的

  1. ImageLoader.getInstance().displayImage(imageUrl, imageView); // imageUrl代表图片的URL地址,imageView代表承载图片的IMAGEVIEW控件

2.加载自定义配置的一个图片的

  1. ImageLoader.getInstance().displayImage(imageUrl, imageView,options); // imageUrl代表图片的URL地址,imageView代表承载图片的IMAGEVIEW控件 , options代表DisplayImageOptions配置文件

3.图片加载时候带加载情况的监听ImageLoadingListener 用于监听图片的下载情况。

imageLoader.displayImage(imageUrl, imageView, options, new ImageLoadingListener() {

@Override

public void onLoadingStarted() {

//开始加载的时候执行

}

@Override

public void onLoadingFailed(FailReason failReason) {

//加载失败的时候执行

}

@Override

public void onLoadingComplete(Bitmap loadedImage) {

//加载成功的时候执行

}

@Override

public void onLoadingCancelled() {

//加载取消的时候执行

}});

4.图片加载时候,带监听又带加载进度条的情况

imageLoader.displayImage(imageUrl, imageView, options, new ImageLoadingListener() {

@Override

public void onLoadingStarted() {

//开始加载的时候执行

}

@Override

public void onLoadingFailed(FailReason failReason) {

//加载失败的时候执行

}

@Override

public void onLoadingComplete(Bitmap loadedImage) {

//加载成功的时候执行

}

@Override

public void onLoadingCancelled() {

//加载取消的时候执行

},new ImageLoadingProgressListener() {

@Override

public void onProgressUpdate(String imageUri, View view, int current,int total) {

//在这里更新 ProgressBar的进度信息

}

});

4、加载其它来源的图片:

1>本地文件

String imagePath = "/mnt/sdcard/image.png";

String imageUrl = Scheme.FILE.wrap(imagePath);

imageLoader.displayImage(imageUrl, mImageView, options);

2>还有来源于Content
provider,drawable,assets中,使用的时候也很简单,我们只需要给每个图片来源的地方加上Scheme包裹起来(Content provider除外),然后当做图片的url传递到imageLoader中,Universal-Image-Loader框架会根据不同的Scheme获取到输入流

//图片来源于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");

三、避免OOM

虽然这个框架有很好的缓存机制,有效的避免了OOM的产生,一般的情况下产生OOM的概率比较小,但是并不能保证OutOfMemoryError永远不发生,这个框架对于OutOfMemoryError做了简单的catch,保证我们的程序遇到OOM而不被crash掉,但是如果我们使用该框架经常发生OOM,我们应该怎么去改善呢?

  • 减少线程池中线程的个数,在ImageLoaderConfiguration中的(.threadPoolSize)中配置,推荐配置1-5
  • 在DisplayImageOptions选项中配置bitmapConfig为Bitmap.Config.RGB_565,因为默认是ARGB_8888, 使用RGB_565会比使用ARGB_8888少消耗2倍的内存
  • 在ImageLoaderConfiguration中配置图片的内存缓存为memoryCache(new WeakMemoryCache()) 或者不使用内存缓存
  • 在DisplayImageOptions选项中设置.imageScaleType(ImageScaleType.IN_SAMPLE_INT)或者imageScaleType(ImageScaleType.EXACTLY)
时间: 2024-10-10 20:35:34

Android开源框架Universal-Image-Loader学习使用1的相关文章

开源项目Universal Image Loader for Android 说明文档 (1) 简介

 When developing applications for Android, one often facesthe problem of displaying some graphical content from the Internet. So, youshould provide image loading from the Web in an Android app, their processingand displaying with limited memory aga

Android开源框架ViewPageIndicator和ViewPager实现Tab导航

前言: 关于使用ViewPageIndicator和ViewPager实现Tab导航,在开发社区里已经有一堆的博客对其进行了介绍,假设我还在这里写怎样去实现.那简直就是老生常谈,毫无新奇感,并且.我也不觉得自己对ViewPageIndicator的理解会比别人好,毕竟我也是看着大神的帖子.在学习实践着. 那我还写这个有啥意义呢?事实上么,就是想在这里记录下.在使用ViewPageIndicator和ViewPager实现Tab导航时,大家有可能会遇到的坑.这个坑.须要我们开发时尽量去避免的. 啥

Android进阶笔记14:RoboBinding(实现了数据绑定 Presentation Model(MVVM) 模式的Android开源框架)

1.RoboBinding RoboBinding是一个实现了数据绑定 Presentation Model(MVVM) 模式的Android开源框架.从简单的角度看,他移除了如addXXListener(),findViewById()这些不必要的代码,连如BufferKnife那样的InjectView都不需要,因为你的代码一般不需要依赖于这些界面组件信息.下面以一个最简单的AndroidMVVM为例. (1)layout 布局 <LinearLayout xmlns:android="

Android开源框架 Android-Universal-Image-Loader

Android开源框架Universal-Image-Loader就像图片加载守护者,为我们提供了丰富的功能特性: (1)多线程加载图像(异步或同步): (2)高度可定制化imageloader配置(线程池.图片下载器.解码器.内存和磁盘缓存.显示图像选项等): (3)每一个显示图像有许多自定义选项(存根图片,缓存开关,解码选项,位图处理和显示等): (4)支持内存和磁盘上的图像缓存(设备的文件系统和SD卡): (5)监听加载过程(包括下载进度): 下来我们详解如何配置使用Universal-I

Android 开源框架Universal-Image-Loader完全解析(二)--- 图片缓存策略详解

本篇文章继续为大家介绍Universal-Image-Loader这个开源的图片加载框架,介绍的是图片缓存策略方面的,如果大家对这个开源框架的使用还不了解,大家可以看看我之前写的一篇文章Android 开源框架Universal-Image-Loader完全解析(一)--- 基本介绍及使用,我们一般去加载大量的图片的时候,都会做缓存策略,缓存又分为内存缓存和硬盘缓存,我之前也写了几篇异步加载大量图片的文章,使用的内存缓存是LruCache这个类,LRU是Least Recently Used 近

greenDao android开源框架数据库更新表的问题

最近使用greenDao当android应用升级数据库新增表或者修改表,发现数据被清空的问题 查找资料也没有找到解决方案,最后查看代码发现需要自己修改SQLiteOpenHelper 1.找到greenDao生成的DaoMaster.java文件,里面有SQLiteOpenHelper实现 2.修改DevOpenHelper类里的   public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) 方法 通过old

android开源框架android-async-http使用

android开源框架android-async-http使用 转:http://www.open-open.com/lib/view/open1369637365753.html         android-async-http开源框架可以是我们轻松的获取网络数据或者向服务器发送数据,使用起来也很简单,下面做简单介绍,具体详细使用看官网:https://github.com/loopj/android-async-http 1.新建项目,去官网下载zip包,解压,打开releases文件,

Android开源框架Afinal第一篇——揭开圣女的面纱

Android开源框架Afinal第一篇——揭开圣女的面纱 分类: Android开源框架哪点事2013-09-02 14:25 260人阅读 评论(0) 收藏 举报 Afinal 这是Afinal在github的地址:https://github.com/yangfuhai/afinal Afinal这个框架主要分4块: 1.FinalDB模块:android中的orm框架,一行代码就可以进行增删改查.支持一对多,多对一等查询. 2.FinalActivity模块:android中的ioc框架

android 开源框架推荐

同事整理的 android 开源框架,个个都堪称经典.32 个赞! 1.volley 项目地址 https://github.com/smanikandan14/Volley-demo (1)  JSON,图像等的异步下载: (2)  网络请求的排序(scheduling) (3)  网络请求的优先级处理 (4)  缓存 (5)  多级别取消请求 (6)  和Activity和生命周期的联动(Activity结束时同时取消所有网络请求) 2.android-async-http  项目地址:ht

Android 开源框架Universal-Image-Loader完全解析(三)---源代码解读

本篇文章主要是带大家从源码的角度上面去解读这个强大的图片加载框架,自己很久没有写文章了,感觉生疏了许多,距离上一篇文章三个月多了,确实是自己平常忙,换了工作很多东西都要去看去理解,然后加上自己也懒了,没有以前那么有激情了,我感觉这节奏不对,我要继续保持以前的激情,正所谓好记性不如烂笔头,有时候自己也会去翻看下之前写的东西,我觉得知识写下来比在脑海中留存的更久,今天就给大家来读一读这个框架的源码,我感觉这个图片加载框架确实写的很不错,读完代码自己也学到了很多.我希望大家可以先去看下Android