listview,gridview局部刷新,部分刷新

众所周知Listview和Gridview的刷新界面的方式是调用adapter.notifyDataSetChanged()进行界面刷新。

但是此方法有其弊端,他是将界面中的数据全部刷新一遍,不论数据有没有变化。如果listview加载了很多的数据(如:100条)

在进行刷新时就会造成很大的系统开销如何像qq空间个人动态那样点赞只刷新一条呢:

主要原理:

对listview的某一个item进行刷新

1.要获取要刷新的item当前索引position和数据

2.对获取的数据进行重置

3.将重置的数据放到adapter中的数据集的原来的位置(根据position刷新原数据集的某一条数据)

4.在listview中获取需要刷新的子item的view

5.从更新过的数据集中获取新数据,更新viwe中的数据(handler中操作,实现界面的刷新)

功能如下,代码中有详细注释:

public class MainActivity extends Activity{private ArrayList<MyListItem> list = null;private ListViewlv;private MyListAdapteradapter;@Overrideprotected void onCreate(Bundle savedInstanceState){super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);intitData();lv = (ListView) findViewById(R.id.listView1);adapter = new MyListAdapter(list, getApplicationContext());adapter.setListView(lv);lv.setAdapter(adapter);lv.setOnItemClickListener(new OnItemClickListener(){@Overridepublic void onItemClick(AdapterView<?> parent, View view, int position, long id){// 获取listview中点击item的数据MyListItem item = (MyListItem) parent.getItemAtPosition(position);Log.i("eee", item.getData() + " == " + item.getPosition());// 更新数据item.setData("update item " + position);// 更新界面adapter.updateItemData(item);}});}/*** 初始化数据*/private void intitData(){list = new ArrayList<MyListItem>();for (int i = 0; i < 20; i++){MyListItem item = new MyListItem();item.setData("item " + i);item.setPosition(i);list.add(item);}}/*** 自定义item数据类型*/class MyListItem{/*** 数据id*/private int dataId;/*** 数据*/private String data;public int getPosition(){return dataId;}public void setPosition(int position){this.dataId = position;}public String getData(){return data;}public void setData(String data){this.data = data;}}}activity进行调用,功能操作主要封装在adapter中如下:

public class MyListAdapter extends BaseAdapter{/*** listview中的数据集*/private ArrayList<MyListItem> mDataList;private ContextmContext;private ListViewmListView;public MyListAdapter(ArrayList<MyListItem> list, Context cont){this.mDataList = list;this.mContext = cont;}/*** 设置listview对象** @param lisv*/public void setListView(ListView lisv){this.mListView = lisv;}/*** update listview 单条数据** @param item 新数据对象*/public void updateItemData(MyListItem item){Message msg = Message.obtain();int ids = -1;// 进行数据对比获取对应数据在list中的位置for (int i = 0; i < mDataList.size(); i++){if (mDataList.get(i).getPosition() == item.getPosition()){ids = i;}}msg.arg1 = ids;// 更新mDataList对应位置的数据mDataList.set(ids, item);// handle刷新界面han.sendMessage(msg);}@SuppressLint("HandlerLeak")private Handler han = new Handler(){public void handleMessage(android.os.Message msg){updateItem(msg.arg1);};};/*** 刷新指定item** @param index item在listview中的位置*/private void updateItem(int index){if (mListView == null){return;}// 获取当前可以看到的item位置int visiblePosition = mListView.getFirstVisiblePosition();// 如添加headerview后 firstview就是hearderview// 所有索引+1 取第一个view// View view = listview.getChildAt(index – visiblePosition + 1);// 获取点击的viewView view = mListView.getChildAt(index – visiblePosition);TextView txt = (TextView) view.findViewById(R.id.textView1);// 获取mDataList.set(ids, item);更新的数据MyListItem data = (MyListItem) getItem(index);// 重新设置界面显示数据txt.setText(data.getData());}@Overridepublic int getCount(){// TODO Auto-generated method stubreturn mDataList.size();}@Overridepublic Object getItem(int position){// TODO Auto-generated method stubreturn mDataList.get(position);}@Overridepublic long getItemId(int position){// TODO Auto-generated method stubreturn position;}@Overridepublic View getView(int position, View convertView, ViewGroup parent){// TODO Auto-generated method stubif (convertView == null){convertView = LayoutInflater.from(mContext).inflate(R.layout.list_item, null);}TextView txt = (TextView) convertView.findViewById(R.id.textView1);txt.setText(mDataList.get(position).getData());return convertView;}}由于listview与gridview功能相似,只是显示方式不同,原理一样,需要的同学可以自己修改一下试试

源码下载

是清晰的又是朦胧的,是一杯苦茶,最后却品出清雅之香。

listview,gridview局部刷新,部分刷新

相关文章:

你感兴趣的文章:

标签云: