由于项目需求,需要实现一个ListView的下拉刷新和上拉加载,每次都与服务器通信请求数据并根据返回值更新当前数据,由于ListView的灵活性及其应用的广泛性,其在Android中会有很多地方遇到诸如此类的需要刷新和加载的问题,但先生还是第一次来实现,遇到了N多坑,为了以后绕远点儿,故来此把遇到的问题和解决方法留念吧
*****************************************************************
首先,先生用的是一个前辈给的已经封装好的PullToRefreshListView,在应用前需要把PullToRefreshListView覆盖掉前面ListView在Layout中的位置,然后用getRefreshableView,从已经封装好的PullToRefreshListView得到后面加SimpleAdapter的ListView:
mPullListView = (PullToRefreshListView) this.findViewById(R.id.mlistView);
mPullListView.setPullLoadEnabled(true);
mPullListView.setScrollLoadEnabled(true);
listView = mPullListView.getRefreshableView();
上面就是从布局得到PullToRefreshListView并设置可以下拉刷新和上拉加载,最后得到ListView的过程。
再后面就是给mPullListView设置监听器,监听下拉和上拉的动作:
mPullListView
.setOnRefreshListener(new mPullListViewOnRefreshListener());
setLastUpdateTime();
下面的就是Listener:
//监听下拉和上拉
private class mPullListViewOnRefreshListener implements
PullToRefreshListView.OnRefreshListener<ListView> {
@Override
public void onPullDownToRefresh(PullToRefreshBase<ListView> refreshView) {
// TODO Auto-generated method stub
PullIsDown = true;
new GetDataTask().execute();
}
@Override
public void onPullUpToRefresh(PullToRefreshBase<ListView> refreshView) {
// TODO Auto-generated method stub
PullIsDown = false;
new GetDataTask().execute();
}
}
在GetDataTask()中实现开一个后台线程从服务器得到数据的过程,GetDataTask继承自AsyncTask,关于AsyncTask读者们可以去参考其他的博客,AsyncTask也就是从子线程转到UI线程的一个轻量级线程,这里先生犯了一个现在还在后悔的错误,由于之前已经写了一个开线程并获取数据的Thread,所以我在GetDataTask中的doInBackground中就直接调用Thread来实现数据传输了,简而言之就是在一个子线程中又开了一个线程实现数据传输,这样做有以下几点不安全的问题:
1、子线程中又开启其他的线程,这样在Android中是绝对不安全的,并且开启另一个Thread的初始目的就是在Android的UI线程中是不允许数据通信的,在Thread中实现的完全可以在GetDataTask中实现。
2、AsyncTask默认doInBackground完成后不久就调用onPostExecute,先生是在onPostExecute实现adapter.notifyDataSetChanged(),刷新ListView的,像先前做的话,开启Thread的线程,doInBackground就默认“我做完事了,调用onPostExecute吧”,这样,在notifyDataSetChanged的时候,Thread并没有完成数据通信,刷新就更不用说了。
***********************************************************
在完成上面问题后,下拉刷新就没什么问题了,但是,在开发过程中BUG是数不完的,接下来就是上拉加载的问题了:
在调试过程中,由于每次显示的上拉加载都没什么问题,但是在于从服务器得到的数据做对比时,才发现,每次加载之后只是显示出加载的状态,但是ListView并没有在UI中加载得到的数据,调试了N个多小时,在差点放弃自己解决,准备去问前辈时,发现在自定义的SimpleAdapter中是不是因为没有重写getCount呢?之前在继承自SimpleAdapter,重写时,仅仅重写了构造方法和getView,把getCount加上,并返回Lists的size,就成功实现了上拉加载更多的功能。
************************************************************
在修改BUG的时候,遇到的问题不仅仅上面的那些,但是重要的是我们对待这些问题的态度,端正态度,一步一步的调试,发现问题,到最后对这类的问题都知根知底,是学习的关键。
最后,大家可以看一下前辈给的已近封装好的PullToRefreshListView,在此感谢前辈对先生这些日子的指导。
http://download.csdn.net/detail/jt_1120112216/7689647