Andriod RecyclerView 适配器与点击事件
发布日期:2021-05-07 23:05:22 浏览次数:17 分类:原创文章

本文共 12974 字,大约阅读时间需要 43 分钟。



文章目录




























1 RecyclerView 简介



  • RecyclerView是Android5.0后谷歌推出的一个用于在有限的窗口中展示大量数据集的控件,它可以称为增强版的listview

  • 不仅可以轻松实现和listview一样的效果,同时又优化了listview的不足之处


1.1 RecyclerView 特点



  1. 支持局部刷新

  2. 可以自定义item增删时的动画

  3. 能够实现item拖拽和侧滑删除等功能

  4. 默认已实现View的复用,而且回收机制更加完善


1.2 基本使用



  • 由于RecyclerView 不再Andriod SDK中, 所以要使用androidx.recyclerview.widget.RecyclerView 进行引用


<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    xmlns:app="http://schemas.android.com/apk/res-auto"    xmlns:tools="http://schemas.android.com/tools"    android:layout_width="match_parent"    android:layout_height="match_parent"    android:orientation="vertical"    tools:context=".MainActivity">    <androidx.recyclerview.widget.RecyclerView        android:id="@+id/recycler_view"        android:layout_width="match_parent"        android:layout_height="match_parent"        /></LinearLayout>

2 创建ReCyclerView 适配器



  • 继承于RecyclerView.Adapter<VH>

  • 其中VH是我们创建的一个继承于RecyclerView.ViewHolder的静态内部类


该适配器类主要有3个方法和1个自定义ViewHolder组成



  1. onCreateViewHolder: 创建ViewHolder并返回,后续item布局里控件都是从ViewHolder中取出

  2. onBindViewHolder:通过方法提供的ViewHolder,将数据绑定到ViewHolder

  3. getItemCount:获取数据源总长度



  • 使用时,设置到RecyclerViewrecycleview.setAdapter(adapter);


2.1 FruitAdapter 实例



  1. 在构造函数中public FruitAdapter(List<Fruit> fruits) 传入数据源


  2. 创建ViewHolder 内部类: public class ViewHolder extends RecyclerView.ViewHolder


  3. 重写RecyclerAdapter的三个方法




  • public FruitAdapter.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) 中进行布局填充,并保存到ViewHoler; 可以对ViewHolder中的控件设置监听事件

  • public void onBindViewHolder(@NonNull FruitAdapter.ViewHolder holder, int position) 中设置ViewHoder 中控件的内容

  • public int getItemCount() 中获取数据源的长度


import android.view.LayoutInflater;import android.view.View;import android.view.ViewGroup;import android.widget.ImageView;import android.widget.TextView;import android.widget.Toast;import androidx.annotation.NonNull;import androidx.recyclerview.widget.RecyclerView;import java.util.List;public class FruitAdapter extends RecyclerView.Adapter<FruitAdapter.ViewHolder> {
/** * 1. FruitAdapter 继承与RecyclerAdapter, * */ private List<Fruit> fruits; // 1. 构造方法传入数据源 public FruitAdapter(List<Fruit> fruits) {
this.fruits = fruits; } @NonNull @Override // 创建ViewHolder实例, 将加载的布局放到构造函数中,并将View返回 public FruitAdapter.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
// 将填充的view放到viewHolder中 View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.fruit_layout_staggered, parent, false); ViewHolder holder = new ViewHolder(view); // 1. 在创建的时候进行点击事件 // 从viewHolder中获取子空间, 添加点击事件 // 1.1 子布局的点击事件 holder.getFruitView().setOnClickListener(new View.OnClickListener(){
@Override public void onClick(View view1) {
// 获取点击的位置,定位数组并输出信息 int adapterPosition = holder.getAdapterPosition(); Fruit fruit = fruits.get(adapterPosition); Toast.makeText(view1.getContext(), "点击的布局,其中内容为: " + fruit.getName(), Toast.LENGTH_SHORT).show(); } }); // 1.2 获取图片的点击事件 holder.getFruitImage().setOnClickListener(new View.OnClickListener(){
@Override public void onClick(View view2) {
int adapterPosition = holder.getAdapterPosition(); Fruit fruit = fruits.get(adapterPosition); Toast.makeText(view2.getContext(), "点击图片的水果名称为: " + fruit.getName(), Toast.LENGTH_SHORT).show(); } }); // 1.3 为文本框指定点击事件 holder.getFruitName().setOnClickListener(new View.OnClickListener() {
@Override public void onClick(View view3) {
String name = ((TextView)view3.findViewById(R.id.fruit_name)).getText().toString(); Toast.makeText(view3.getContext(), name, Toast.LENGTH_SHORT).show(); } }); return holder; } @Override // 2. 每个子项滚动到屏幕内执行,通过 positon 得到当前项的实例,然后显示图片和文字,填充布局 public void onBindViewHolder(@NonNull FruitAdapter.ViewHolder holder, int position) {
Fruit fruit = fruits.get(position); holder.getFruitImage().setImageResource(fruit.getImageID()); holder.getFruitName().setText(fruit.getName()); holder.getFruitPrice().setText("$" + (double)fruit.getPrice()/100 + "/Kg"); } @Override public int getItemCount() {
return fruits.size(); } public class ViewHolder extends RecyclerView.ViewHolder{
// 添加ViewHolder中的控件 private View fruitView; private ImageView fruitImage; private TextView fruitName; private TextView fruitPrice; public ViewHolder(@NonNull View itemView) {
super(itemView); this.fruitView = itemView; this.fruitImage = itemView.findViewById(R.id.fruit_image); this.fruitName = itemView.findViewById(R.id.fruit_name); this.fruitPrice = itemView.findViewById(R.id.fruit_price); } public void setFruitView(View fruitView) {
this.fruitView = fruitView; } public void setFruitImage(ImageView fruitImage) {
this.fruitImage = fruitImage; } public void setFruitName(TextView fruitName) {
this.fruitName = fruitName; } public void setFruitPrice(TextView fruitPrice) {
this.fruitPrice = fruitPrice; } public ImageView getFruitImage() {
return fruitImage; } public TextView getFruitName() {
return fruitName; } public TextView getFruitPrice() {
return fruitPrice; } public View getFruitView() {
return fruitView; } }}

3 为适配器中的控件指定布局



  • 相对于ListView 只能使用线性布局的局限,RecyclerView 能自定义布局,并通过不同的布局管理器来控制item的排列顺序,负责item元素的布局和复用


RecyclerView提供了三种布局管理器:



  1. LinearLayoutManager:线性布局,以垂直戒水平滚动列表方式显示项目


// 5.1 创建垂直的线性布局LinearLayoutManager layoutManager = new LinearLayoutManager(MainActivity.this);recyclerView.setLayoutManager(layoutManager);


  1. GridLayoutManager:网格布局,在网格中显示项目


// 5.2 创建横向的线性布局LinearLayoutManager linearLayoutManagerHorizontal = new LinearLayoutManager(this);linearLayoutManagerHorizontal.setOrientation(LinearLayoutManager.HORIZONTAL);recyclerView.setLayoutManager(linearLayoutManagerHorizontal);


  1. StaggeredGridLayoutManager:瀑布流布局,在分散对齐网格中显示项目


// 5.3 创建瀑布布局StaggeredGridLayoutManager staggeredGridLayoutManager = new StaggeredGridLayoutManager(3, StaggeredGridLayoutManager.VERTICAL);recyclerView.setLayoutManager(staggeredGridLayoutManager);

4 布局layout文件


4.1 垂直线性子布局xml文件


<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:orientation="horizontal"    android:layout_width="match_parent"    android:layout_height="wrap_content">    <ImageView        android:layout_width="100dp"        android:layout_height="80dp"        android:id="@+id/fruit_image"        android:src="@drawable/apple"        />    <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:id="@+id/fruit_name"        android:text="name"        android:textSize="30sp"        android:textColor="#000000"        android:layout_gravity="center_vertical"        android:layout_marginLeft="20dp"        />        <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:id="@+id/fruit_price"        android:text="name"        android:textSize="30sp"        android:textColor="#ff0000"        android:layout_gravity="center_vertical"        android:layout_marginLeft="40dp"        /></LinearLayout>

4.2 水平线性子布局xml文件


<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:orientation="vertical"    android:layout_width="120dp"    android:layout_height="wrap_content">    <ImageView        android:layout_width="100dp"        android:layout_height="80dp"        android:layout_gravity="center_horizontal"        android:id="@+id/fruit_image"        android:src="@drawable/apple"        />    <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:id="@+id/fruit_name"        android:text="name"        android:textSize="24sp"        android:textColor="#000000"        android:layout_gravity="center"        />    <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:id="@+id/fruit_price"        android:text="12.00"        android:textSize="12sp"        android:textColor="#ff0000"        android:layout_gravity="center"        /></LinearLayout>

4.3 瀑布布局xml文件


<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:orientation="vertical"    android:layout_width="wrap_content"    android:layout_margin="5dp"    android:layout_height="wrap_content">    <ImageView        android:layout_width="100dp"        android:layout_height="80dp"        android:layout_gravity="center_horizontal"        android:id="@+id/fruit_image"        android:src="@drawable/apple"        />    <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:id="@+id/fruit_name"        android:text="name"        android:textSize="24sp"        android:textColor="#000000"        android:layout_gravity="center"        />    <TextView        android:layout_width="wrap_content"        android:layout_height="wrap_content"        android:id="@+id/fruit_price"        android:text="12.00"        android:textSize="12sp"        android:textColor="#ff0000"        android:layout_gravity="center"        /></LinearLayout>

5 Fruit封装数据类


package com.hlq.sz_ch06_recycler_view;public class Fruit {
private int imageID; private String name; private long price; public void setImageID(int imageID) {
this.imageID = imageID; } public void setName(String name) {
this.name = name; } public void setPrice(long price) {
this.price = price; } public int getImageID() {
return imageID; } public String getName() {
return name; } public long getPrice() {
return price; } public Fruit(int imageID, String name, long price) {
this.imageID = imageID; this.name = name; this.price = price; } public Fruit() {
}}

6 MainActivity 主界面


package com.hlq.sz_ch06_recycler_view;import androidx.appcompat.app.AppCompatActivity;import androidx.recyclerview.widget.LinearLayoutManager;import androidx.recyclerview.widget.RecyclerView;import androidx.recyclerview.widget.StaggeredGridLayoutManager;import android.os.Bundle;import android.widget.LinearLayout;import java.util.ArrayList;import java.util.List;public class MainActivity extends AppCompatActivity {
private RecyclerView recyclerView; @Override protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); // 1. 绑定控件 recyclerView = this.findViewById(R.id.recycler_view); // 2. 准备数据 List<Fruit> fruits = new ArrayList<>(); for (int i = 0; i < 10; ++i) {
Fruit pineApple = new Fruit(R.drawable.pineapple, "菠萝", 1690); fruits.add(pineApple); Fruit mango = new Fruit(R.drawable.mango, "芒果", 2990); fruits.add(mango); Fruit grape = new Fruit(R.drawable.grape, "葡萄", 1990); fruits.add(grape); Fruit pomegranate = new Fruit(R.drawable.pomegranate, "石榴", 1500); fruits.add(pomegranate); Fruit apple = new Fruit(R.drawable.apple, "苹果", 2000); fruits.add(apple); Fruit watermelon = new Fruit(R.drawable.watermelon, "西瓜", 2880); fruits.add(watermelon); Fruit orange = new Fruit(R.drawable.orange, "橘子", 1880); fruits.add(orange); } // 3. 设计子布局 // 4. 创建自定义适配器 FruitAdapter adapter = new FruitAdapter(fruits); // 5. 创建布局管理器,将RecyclerView中的布局以布局管理器中的布局进行管理// // 5.1 创建垂直的线性布局// LinearLayoutManager layoutManager = new LinearLayoutManager(MainActivity.this);// recyclerView.setLayoutManager(layoutManager);// // 5.2 创建横向的线性布局// LinearLayoutManager linearLayoutManagerHorizontal = new LinearLayoutManager(this);// linearLayoutManagerHorizontal.setOrientation(LinearLayoutManager.HORIZONTAL);// recyclerView.setLayoutManager(linearLayoutManagerHorizontal); // 5.3 创建瀑布布局 StaggeredGridLayoutManager staggeredGridLayoutManager = new StaggeredGridLayoutManager(3, StaggeredGridLayoutManager.VERTICAL); recyclerView.setLayoutManager(staggeredGridLayoutManager); // 6 绑定 布局-控制-数据的适配器 recyclerView.setAdapter(adapter); }}

7 结果


在这里插入图片描述

上一篇:Andriod RecyclerView的点击事件
下一篇:Andriod 自定义ListView的列表项

发表评论

最新留言

做的很好,不错不错
[***.243.131.199]2025年04月11日 21时27分15秒