高级控件ListView

  1. BaseAdapter:是所有适配器类的父类,可以对列表项进行最大限度的定制
    1.1 自定义适配器中的方法
    getCount
    getView
    getItem
    getItemId
    1.2 LayoutInflater(布局解析器)
    –LayoutInflater有三种获得方式,资料中有详细介绍
    用来把layout布局文件解析成一个View对象,不可以new,需要使用系统服务获得
    inflater = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE);

案例一:ListView的使用及优化
2. ListView优化
2.1 使用ConvertView重用组件
即拖动时被遮住、看不见的控件,重用它,而非每次创建一个新的对象

2.2 使用内部类ViewHolder+ConvertView.setTag()保存控件,而不用每次查找
ViewHolder(视图的持有者)

2.3 使用分页查询(PullToRefresh)
2.3.2 使用AsyncTask(异步任务)加载数据,最少要重写以下这两个方法
doInBackground
后台执行
onPostExecute
在doInBackground方法执行结束之后在运行,并且运行在UI线程当中 可以对UI空间进行设置
关键代码:
myListViewAdapter.notifyDataSetChanged();// 通知适配器数据已改变
ptrlv_main_1.onRefreshComplete();// 通知控件数据已经加载完毕

2.4 事件监听的优化
假设Item中有三个按钮,要为三个按钮定义事件,如果是下面这样
btn1.setOnclickListener(new View.onClickListener(){
public void onClick(View view){
//…
}
});
btn2.setOnclickListener(new View.onClickListener(){
public void onClick(View view){
//…
}
});
btn3.setOnclickListener(new View.onClickListener(){
public void onClick(View view){
//…
}
});
如果每屏显示10个Item,那一共创建了30个listener对象在内存中。
如果,你是在Adapter创建时,只创建一个Listener,并将其定义成全局属性,
然后通过按钮的ID来进行判断是哪个事件应该触发,
class MyAdapter extends BaseAdapter{
View.onClickListener myListener = new View.onClickListener(){
public void onClick(View view){
if(view.getId() == R.id.btn1){
//…
}else if(view.getId() == R.id.btn2){
//…
}else if(view.getId() == R.id.btn3){
//…
}
}
});
}

    //注册监听器
    btn1.setOnclickListener(myListener);
    btn2.setOnclickListener(myListener);
    btn3.setOnclickListener(myListener);

2.5 另外,真实开发中,图片肯定是通过网络下载,也需要通过线程异步下载进行优化等等,但由于还涉及到android网络编程,
这部分的内容会在之后的课程中介绍

  1. 第三方控件:上拉加载、下拉刷新控件
    3.1 导入第三方插件库
    Android-PullToRefresh-master.zip

    3.2 在布局文件中使用第三方插件
    com.handmark.pulltorefresh.library.PullToRefreshListView

    3.3 自定义适配器(BaseAdapter)提供数据

    3.4 异步任务查询数据(AsyncTask)
    3.4.1 AsyncTask定义了三种泛型类型 Params,Progress和Result。
    Params 启动任务执行的输入参数,比如HTTP请求的URL。
    Progress 后台任务执行的百分比。
    Result 后台执行任务最终返回的结果,比如String
    3.4.2 异步加载数据最少要重写以下这两个方法
    doInBackground(Params…) 后台执行,比较耗时的操作都可以放在这里
    onPostExecute(Result) 相当于Handler 处理UI的方式,在这里面可以使用在doInBackground 得到的结果处理操作UI
    –注:此方法中再通知适配器和控件
    myBaseAdapter.notifyDataSetChanged();// 通知适配器数据已改变
    plv_main_plv1.onRefreshComplete();// 通知控件数据已经加载完毕

    3.5 给PullToRefreshListView设置相关属性
    plv_main_1.setMode(Mode.BOTH);// 设置刷新模式
    Mode.BOTH:同时支持上拉下拉
    Mode.PULL_FROM_START:只支持下拉Pulling Down
    Mode.PULL_FROM_END:只支持上拉Pulling Up

    plv_main_1.getLoadingLayoutProxy().setPullLabel(“上拉刷新…”);// 刚下拉时,显示的提
    plv_main_1.getLoadingLayoutProxy().setRefreshingLabel(“正在载入…”);// 刷新时
    plv_main_1.getLoadingLayoutProxy().setReleaseLabel(“放开刷新…”);// 下来达到一定距离时,显示的提示

    3.6 给PullToRefreshListView设置适配器

    3.7 给PullToRefreshListView设置监听器
    监听器有二种:第一种上拉和下拉刷新的效果是一样的,要想实现上拉和下拉刷新效果不一样就要使用第二种
    setOnRefreshListener/PullToRefreshBase.OnRefreshListener

    setOnRefreshListener2/PullToRefreshBase.OnRefreshListener2

核心:
1、listview控件、项资源、自定义适配器准备好
2、向服务端拿数据
3、初始化自定适配器(获取视图解析器、得到项资源的view控件、获取所有的子控件,给子控件赋值、返回view)
4、绑定适配器

这里写图片描述

public class MainActivity extends AppCompatActivity {

private List<Book> data;
private MyBaseAdapter adapter;
private ListView lv_main_bookList;


@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    lv_main_bookList = findViewById(R.id.lv_main_bookList);

    this.data = new BookDao().list();
    adapter = new MyBaseAdapter((LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE));
    lv_main_bookList.setAdapter(adapter);
}

public class MyBaseAdapter extends BaseAdapter{
    public class ViewHolder{
        ImageView iv_listviewitem_image;
        TextView tv_listviewitme_title;
        TextView tv_listviewitme_author;
        TextView tv_listviewitme_price;
        TextView tv_listviewitme_publish;
        TextView tv_listviewitme_remark;

    }
    private LayoutInflater inflater;

    public MyBaseAdapter(LayoutInflater inflater) {
        this.inflater = inflater;
    }

    @Override
    public int getCount() {
        return data.size();
    }

    @Override
    public Object getItem(int position) {
        return data.get(position);
    }

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

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        View v = convertView;
        if(v == null){
            ViewHolder vh = new ViewHolder();
            Log.i("test","position:"+position);
            v = inflater.inflate(R.layout.listview_item,null);
            vh.iv_listviewitem_image = v.findViewById(R.id.iv_listviewitem_image);
            vh.tv_listviewitme_title = v.findViewById(R.id.tv_listviewitme_title);
            vh.tv_listviewitme_author = v.findViewById(R.id.tv_listviewitme_author);
            vh.tv_listviewitme_price = v.findViewById(R.id.tv_listviewitme_price);
            vh.tv_listviewitme_publish = v.findViewById(R.id.tv_listviewitme_publish);
            vh.tv_listviewitme_remark = v.findViewById(R.id.tv_listviewitme_remark);
            v.setTag(vh);
        }


        ViewHolder vh = (ViewHolder) v.getTag();

        Book book = data.get(position);
        vh.iv_listviewitem_image.setImageResource(book.getImage());
        vh.tv_listviewitme_title.setText(book.getTitle());
        vh.tv_listviewitme_author.setText(book.getAuthor());
        vh.tv_listviewitme_price.setText(book.getPrice()+"");
        vh.tv_listviewitme_publish.setText(book.getPublish());
        vh.tv_listviewitme_remark.setText(book.getRemark());
        return v;
    }
}

}

效果如图:
这里写图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值