ListView單條item刷新

ListView單條item刷新

在使用listView顯示很多數據時當有一條數據發送改變需要刷新某條數據時,一般會調用Adapter.notifyDataSetChanged()來進行刷新。 但會造成體驗不好,尤其是下載列表會高頻率調動Adapter.notifyDataSetChanged()會造成UI繪製資源的浪費進而影響性能。

代碼模塊Activity

public class ActivityA extends AppCompatActivity {

    ListView listView;
    MyAdapter myAdapter = null;
    List<String> datas;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setDatas();
        myAdapter = new MyAdapter(this, datas);
        listView = new ListView(this);
        setContentView(listView);
        listView.setAdapter(myAdapter);

    }

    public void setDatas() {
        datas = new ArrayList<>();

        for (int index = 0; index < 30; index++) {
            datas.add("第" + index + "條數據");
        }
    }
}

代碼適配器

public class MyAdapter extends BaseAdapter {

    private List<String> mData;
    private Context mCtx;
    private LayoutInflater inflater;

    public MyAdapter(Context context, List<String> data) {
        this.mCtx = context;
        this.mData = data;
        notifyDataSetChanged();
        inflater = LayoutInflater.from(mCtx);
    }

    @Override
    public int getCount() {
        return mData == null ? 0 : mData.size();
    }

    @Override
    public String getItem(int position) {
        return mData.get(position);
    }

    @Override
    public long getItemId(int position) {
        return 0;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewHolder holder = null;
        if (convertView == null) {
            convertView = inflater.inflate(R.layout.adapter_layout, parent);
            holder = new ViewHolder();
            holder.tv = convertView.findViewById(R.id.tv);
            convertView.setTag(holder);
        } else {
            holder = (ViewHolder) convertView.getTag();
        }
        holder.tv.setText(getItem(position));
        return convertView;
    }

    class ViewHolder {
        TextView tv;
    }
}

下面列舉局部刷方式:

一、更新對於View的內容

    /**
     * 方法一:更新對應View的內容
     */
    private void upItemView() {
        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                datas.set(position, "我被點擊了,請更新第" + position + "條數據");
         /**第一個可見的位置**/
                int firstVisiblePosition = listView.getFirstVisiblePosition();
                 /**最後一個可見的位置**/
                int lastVisiblePosition = listView.getLastVisiblePosition();
                /**在看見範圍內才更新,不可見的滑動後自動會調用getView方法更新**/
                if (position >= firstVisiblePosition && position <= lastVisiblePosition) {
                    View childView = listView.getChildAt(position - firstVisiblePosition);
                    TextView textView = childView.findViewById(R.id.tv);
                    textView.setText(datas.get(position));
                }
            }
        });
    }

二、使用Adapter.getView方法更新局部數據(這種方法是調用適配器對應的getView方法,用它裏面的代碼對界面進行刷新。這也是google在IO大會上推薦的做法

    /**
     * 二、使用Adapter.getView方法更新局部數據
     */
    private void upItemView() {
        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                datas.set(position, "我被點擊了,請更新第" + position + "條數據");

                int firstVisiblePosition = listView.getFirstVisiblePosition();
                int lastVisiblePosition = listView.getLastVisiblePosition();
                /**在看見範圍內才更新,不可見的滑動後自動會調用getView方法更新**/
                if (position >= firstVisiblePosition && position <= lastVisiblePosition) {
                    View childView = listView.getChildAt(position - firstVisiblePosition);
                    myAdapter.getView(position, childView, listView);
                }
            }
        });
    }
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章