Android ListView&异步加载的学习(四)——完善ListView滑动效率问题
来源:互联网 发布:linux mkdir 权限 编辑:程序博客网 时间:2024/05/21 15:48
ListView中每一项的Item可能包含一个复杂的内容,而用户在使用时既要加载数据又要滑动ListView,有时会造成ListView的卡顿现象,因此需要进行完善。
考虑到的解决这一问题的思想是:使ListView滑动过程中不加载任何异步任务,停止后再加载可见项。
----数据适配器实现整个ListView的滑动事件监听器接口,并实现其中的方法。整体思想:判断当前ListView的滚动状态,如果处于滚动过程中则停止加载可见项,停止滚动后再加载可见项。
----onScroll方法中有两个形参:int firstVisibleItem第一个可见元素,int visibleItemCount可见元素长度。因此在适配器类中声明两个int类型的成员变量mStart,mEnd记录开始和终止的可见元素;声明一个String数组记录url地址,通过mStart和mEnd决定加载String数组中哪一段的数据(onScroll方法的作用就在于不断获取当前的第一个和最后一个可见项);在构造方法中初始化该string类型数组,以for循环将图片的url传入静态数组
public NewsAdapter(Context context,List<NewsBean> data){ mList=data; mInflater=LayoutInflater.from(context); mImageLoader=new ImageLoader(); URLS=new String[data.size()]; for (int i=0;i<data.size();i++){ URLS[i]=data.get(i).newsIconURL;//图片的url转入静态数组 } }
----ImageLoader.java文件中添加一个加载从mStart到mEnd的url数据的方法LoadImages,仿照从AsyncTask中读取url的步骤,加载从start到end的所有图片:
public void loadImages(int start,int end){ for(int i=start;i<end;i++){ String url=NewsAdapter.URLS[i]; Bitmap bitmap=getBitmapFromCache(url); if(bitmap==null) { NewsAsyncTask task=new NewsAsyncTask(url); task.execute(url); mTask.add(task); }else{ ImageView imageView= (ImageView) mListView.findViewWithTag(url); imageView.setImageBitmap(bitmap); } } }
但此时不是再向整个ImageView中读取url,而是向指定的起始和终止位置之间读取数据,因此NewsAsyncTask(imageView, url).execute(url);以及imageView.setImageBitmap(bitmap);语句中向imageView传递url是不合适的,用ListView就能找到ImageView。需要给ImageLoader声明新的成员变量private ListView mListView;和private Set<NewsAsyncTask> mTask;并在构造方法中进行初始化:mListView=listview; mTask=new HashSet<>();;在onPostExecute方法中通过找到的ImageView去设置bitmap;设置完bitmap之后代表这个Task已经结束了,需要在集合中remove掉这个AsyncTask。
class NewsAsyncTask extends AsyncTask<String,Void,Bitmap>{ // private ImageView mImageView; private String mUrl; public NewsAsyncTask(String url){ /*mImageView = imageView;*/ mUrl=url; } @Override protected Bitmap doInBackground(String... params) { Bitmap bitmap=getBitmapFromUrl(params[0]); if (bitmap!=null){ addBitmapToCache(params[0], bitmap); } return bitmap; } @Override protected void onPostExecute(Bitmap bitmap) {//将Bitmap传递给ImageView super.onPostExecute(bitmap); ImageView imageView= (ImageView) mListView.findViewWithTag(mUrl); if (imageView!=null&&bitmap!=null){ imageView.setImageBitmap(bitmap); } mTask.remove(this); } }
----**不要忘记注册接口——注册对应的事件:listView.setOnScrollListener(this);
以上,实现了将显示图片的控制权从getView转换到了滑动监听事件。但是发现初次启动程序时图片是不加载的,想到的原因在于,在第一次启动ListView的时候是默认ListView的状态没有发生改变的,而onScrollStateChanged方法在初次运行时不会自动调用。要进行完善。解决问题的思路:虽然onScrollStateChanged方法在初次运行时不会自动调用,,但是onScroll方法会调用,因此在适配器类中增加一个成员变量Flag来判断是否是第一次启动,并在初始化时赋值为true——private boolean mFirstIn; mFirstIn=true;;在onScroll方法中增加判断语句判断是否是第一次加载且屏幕上的item大于0,若是则将start和end传递给loadImages()方法,人为的显示第一屏的数据;之后将flag设置为false,此后不会再走这一步的逻辑,通过onScrollStateChanged方法来加载图片
public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) { //firstVisibleItem第一个可见元素,visibleItemCount可见元素长度 mStart=firstVisibleItem; mEnd=firstVisibleItem+visibleItemCount; if (mFirstIn&&visibleItemCount>0){ mImageLoader.loadImages(mStart,mEnd); mFirstIn=false; } }以上完成了对ListView加载图片执行效率的全部优化。
总结:此例完成的是一级缓存——将加载内容缓存到内存,其余的还有将内容缓存到硬盘等,可以使用DiskLruCache这个第三方的类来实现“二级缓存”。异步加载不仅是获取网络资源,可以将任何耗时操作都看成异步加载,所有通过耗时操作获取的结果都可以通过缓存来提高效率。但是Cache也存在缺点——不能保证数据使实时的,所以在realtime需求高的应用中不能使用缓存。而对于本地资源,很少用到缓存。
- Android ListView&异步加载的学习(四)——完善ListView滑动效率问题
- android ListView的滑动效率问题
- ListView的滑动效率问题
- Android ListView&异步加载的学习(二)——多线程加载图片
- Android ListView&异步加载的学习(一)
- Android ListView&异步加载的学习(三)——AsyncTask加载图片&运用Lru算法优化图片加载
- 个人记录1-解决listview异步加载图片错位,滑动listview错乱抖动的问题
- Android如何提高ListView的滑动效率
- Android ListView滑动加载
- Android listView 滑动加载
- android 滑动加载listview
- Android ListView异步加载图片错位问题
- android listview 滚动时异步加载图片的问题
- android listview 滚动时异步加载图片的问题
- Android ListView图片异步加载时,图片错位的问题
- Android ListView和异步加载图片的问题
- Android ListView 异步加载图片错位的问题
- Android ListView 异步加载图片错位的问题
- 再谈Qt实现Rasdial拨号问题(说说项目中遇到的问题和解决方案)
- HDU 1396 Counting Triangles
- Linux下安装Eclipse及解决谷歌被墙无法更新SDK问题
- 今天一天都在忙论文的事情,所以今天没时间来学习c++,那就给大家带来一个简单小程序杨辉三角把
- iOS多线程与网络开发之大文件下载 (边下边写/暂停恢复下载/压缩解压zip/多线程下载)
- Android ListView&异步加载的学习(四)——完善ListView滑动效率问题
- Timer的使用
- 文件读写操作
- 改进粒子系统-GPU实现
- 确认对话框
- 安卓环境的搭建(8.7)
- hdu 1058 Humble Number
- Linux之文件操作(3)
- CS224d lecture 12札记