在加载网络图片的时候,通常需要一定的时间来获取网络上的图片文件,以及获取到之后进行略缩图处理。通常将图片加载放在一个子线程中处理
这里介绍一种比较简单的图片异步加载方式
首先,创建一个Loader类,用于处理图片加载
在类里面定义一个静态的HashMap用于缓存获取过的图片drawable资源
//根据url缓存drawable资源
private static HashMap<String, SoftReference<Drawable>> imageCache;
public Loader() {
if (imageCache == null)
this.imageCache = new HashMap<>();
}
public Drawable loadImage(final String url, final LoadCallback callback){
//查看hashMap,如果已经缓存了图片drawable资源则直接返回
Drawable cacheDrawable=null;
if(imageCache.containsKey(url)){
cacheDrawable= imageCache.get(url).get();
}
if(cacheDrawable!=null) return cacheDrawable;
//如果没有缓存则进行异步加载
//使用handler在不同线程中传递数据
final Handler handler=new Handler(){
@Override
public void handleMessage(Message msg) {
//调用回调接口通知Activity更新数据
callback.onLoadImage((Drawable) msg.obj);
}
};
new Thread(){
public void run(){
//在线程中进行网络通信取得图片资源
Drawable drawable=null;
try {
//网络通信,得到输入流
URLConnection connection=new URL(url).openConnection();
InputStream in=connection.getInputStream();
//调用Drawable的特定构造函数,根据输入流创建drawable drawable=Drawable.createFromStream(in,"src");
//将得到的drawable通过handler机制传递出去
Message msg=handler.obtainMessage(0,drawable);
handler.sendMessage(msg);
//将drawable缓存到imageCache
imageCache.put(url,new SoftReference<Drawable>(drawable));
} catch (IOException e) {
e.printStackTrace();
}
}
}.start();
return null;
}
public static interface LoadCallback{
void onLoadImage(Drawable drawable);
}
这里展示一个ListView展示图片的例子,定义了一个Adapter继承自ArrayAdapter,重点在于重写LisView的getView()方法
ListView 异步加载图片
public static class CacheView{
private View view;
private ImageView imageView;
public CacheView(View view){
this.view=view;
}
public ImageView getImageView(){
if(imageView==null)
imageView=(ImageView)view.findViewById(R.id.iv);
return imageView;
}
}
//getView方法内部,用静态内部类cacheView来优化ListView的性能
CacheView cacheView=null;
if(convertView==null){
convertView= LayoutInflater.from(getContext()).inflate(R.layout.list_cell,null,false);
cacheView=new CacheView(convertView);
convertView.setTag(cacheView);
}
cacheView= (CacheView) convertView.getTag();
ImageView imageView=cacheView.getImageView();
final String imageUrl=getItem(position);;
imageView.setTag(imageUrl);
Drawable drawable=asyncImageLoader.loadImage(imageUrl,
new Loader.LoadCallback() {
@Override
public void onLoadImage(Drawable drawable) {
ImageView imageViewByTag = (ImageView) listView.findViewWithTag(imageUrl);
if (imageViewByTag != null)
imageViewByTag.setImageDrawable(drawable);
}
});
if(drawable==null)
imageView.setImageResource(android.R.drawable.sym_def_app_icon);
else
imageView.setImageDrawable(drawable);
return convertView;