Android之RecyclerView轻松实现下拉刷新和加载更多

青春须早为,岂能长少年。这篇文章主要讲述Android之RecyclerView轻松实现下拉刷新和加载更多相关的知识,希望能为你提供帮助。
  今天研究了下RecyclerView的滑动事件,特别是下拉刷新和加载更多事件,在现在几乎所有的APP显示数据列表时都用到了。自定义RecyclerView下拉刷新和加载更多听上去很复杂,实际上并不难,只要是对滑动事件的监听和处理。
一、自定义RecyclerView实现下拉刷新和加载更多
1、如何判断RecyclerView是在上滑还是下滑
在RecyclerView的OnScrollListener滑动事件监听中有个好用的方法,就是onScrolled(RecyclerView recyclerView, int dx, int dy),其中根据dx的值的正负就可以判断是在左滑还是右滑,而根据dy的值就可以判断是在上滑还是下滑。

1 //上滑 2 if(dy> 0){ 3 //相应操作代码 4 } 5 //下滑 6 else if(dy< 0){ 7 //相应操作代码 8 }

2、如何判断是否滑到了顶部或者底部
同样在RecyclerView的OnScrollListener滑动事件监听中onScrolled(RecyclerView recyclerView, int dx, int dy)方法中处理,根据canScrollVertically(int direction)来进行判断。
1 //是否滑到底部 2 if(!recyclerView.canScrollVertically(1)){ 3//相应处理操作 4 } 5 //是否滑到顶部 6 if(!recyclerView.canScrollVertically(-1)){ 7//相应处理操作 8 }

3、自定义RecyclerView
知道了滑动事件的判断和处理,就可以很轻松得实现下拉刷新和加载更多了。
1 import android.content.Context; 2 import android.support.annotation.Nullable; 3 import android.support.v7.widget.RecyclerView; 4 import android.util.AttributeSet; 5 import android.util.Log; 6 7 /** 8* Package:com.liuting.library 9* author:liuting 10* Date:2017/2/14 11* Desc:自定义RecycleView,下拉刷新以及上拉加载更多 12*/ 13 14 public class RefreshLoadMoreRecycleView extends RecyclerView { 15private Boolean isLoadMore; //是否可以加载更多标志 16private Boolean isLoadEnd; //加载到最后的标志 17private Boolean isLoadStart; //顶部的标志 18private Boolean isRefresh; //是否可以下拉刷新标志 19private int lastVisibleItem; //最后一项 20private IOnScrollListener listener; //事件监听 21 22public RefreshLoadMoreRecycleView(Context context) { 23super(context); 24init(context); 25} 26 27public RefreshLoadMoreRecycleView(Context context, @Nullable AttributeSet attrs) { 28super(context, attrs); 29init(context); 30} 31 32public RefreshLoadMoreRecycleView(Context context, @Nullable AttributeSet attrs, int defStyle) { 33super(context, attrs, defStyle); 34init(context); 35} 36 37public void init(Context context) { 38isLoadEnd=false; 39isLoadStart =true; 40 41this.addOnScrollListener(new RecyclerView.OnScrollListener() { 42@Override 43public void onScrollStateChanged(RecyclerView recyclerView, int newState) { 44super.onScrollStateChanged(recyclerView, newState); 45//SCROLL_STATE_DRAGGING和SCROLL_STATE_IDLE 两种效果自己看着来 46if (newState == RecyclerView.SCROLL_STATE_IDLE) { 47if (isLoadEnd) { 48// 判断是否已加载所有数据 49if (isLoadMore) {//未加载完所有数据,加载数据,并且还原isLoadEnd值为false,重新定位列表底部 50if (getListener() != null) { 51getListener().onLoadMore(); 52} 53} else {//加载完了所有的数据 54if(getListener()!=null){ 55getListener().onLoaded(); 56} 57} 58isLoadEnd = false; 59} else if (isLoadStart) { 60if(isRefresh){ 61if (getListener() != null) { 62getListener().onRefresh(); 63} 64isLoadStart=false; 65} 66} 67 68} 69} 70 71@Override 72public void onScrolled(RecyclerView recyclerView, int dx, int dy) { 73super.onScrolled(recyclerView, dx, dy); 74//上滑 75if(dy> 0){ 76//是否滑到底部 77if(!recyclerView.canScrollVertically(1)){ 78isLoadEnd = true; 79}else{ 80isLoadEnd = false; 81} 82} 83//下滑 84else if(dy< 0){ 85//是否滑到顶部 86if(!recyclerView.canScrollVertically(-1)){ 87isLoadStart=true; 88}else{ 89isLoadStart=false; 90} 91} 92} 93}); 94} 95 96//监听事件 97public interface IOnScrollListener { 98void onRefresh(); 99 100void onLoadMore(); 101 102void onLoaded(); 103} 104 105public IOnScrollListener getListener() { 106return listener; 107} 108 109public void setListener(IOnScrollListener listener) { 110this.listener = listener; 111} 112 113public Boolean getLoadMore() { 114return isLoadMore; 115} 116 117//设置是否支持加载更多 118public void setLoadMoreEnable(Boolean loadMore) { 119isLoadMore = loadMore; 120} 121 122public Boolean getRefresh() { 123return isRefresh; 124} 125 126//设置是否支持下拉刷新 127public void setRefreshEnable(Boolean refresh) { 128isRefresh = refresh; 129} 130 }

二、实际用例
已经定义好了RecyclerView,下面在Demo中实际使用和处理。
【Android之RecyclerView轻松实现下拉刷新和加载更多】1、定义布局
布局文件很简单,就是一个RecyclerView
1 < ?xml version="1.0" encoding="utf-8"?> 2 < LinearLayout 3xmlns:android="http://schemas.android.com/apk/res/android" 4xmlns:tools="http://schemas.android.com/tools" 5android:id="@+id/activity_main" 6android:layout_width="match_parent" 7android:layout_height="match_parent" 8android:orientation="vertical" 9tools:context="com.liuting.refreshloadmorelistview.MainActivity"> 10 11< com.liuting.library.RefreshLoadMoreRecycleView 12android:id="@+id/main_recycle_view_data" 13android:layout_width="match_parent" 14android:layout_height="match_parent" 15android:scrollbars="none" 16/> 17 < /LinearLayout>

2、定义RecyclerView.Adapter
RecyclerView.Adapter在这里就简单处理了,列表布局直接使用Android自带的。
1 import android.content.Context; 2 import android.support.v7.widget.RecyclerView; 3 import android.view.LayoutInflater; 4 import android.view.View; 5 import android.view.ViewGroup; 6 import android.widget.TextView; 7 8 import java.util.List; 9 10 /** 11* Package:com.liuting.refreshloadmorelistview.adapter 12* author:liuting 13* Date:2017/2/16 14* Desc:列表Adapter 15*/ 16 17 public class RefreshLoadMoreRecycleAdapter extends RecyclerView.Adapter< RefreshLoadMoreRecycleAdapter.ViewHolder> { 18private List< String> list; 19private Context context; 20 21public RefreshLoadMoreRecycleAdapter(Context context,List< String> list) { 22this.context =context; 23this.list = list; 24} 25 26@Override 27public RefreshLoadMoreRecycleAdapter.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { 28View view = LayoutInflater.from(parent.getContext()).inflate(android.R.layout.simple_expandable_list_item_1, parent, false); 29RefreshLoadMoreRecycleAdapter.ViewHolder viewHolder = new RefreshLoadMoreRecycleAdapter.ViewHolder(view); 30return viewHolder; 31} 32 33@Override 34public void onBindViewHolder(ViewHolder holder, int position) { 35holder.text.setText(list.get(position)); 36holder.itemView.setTag(position); 37} 38 39@Override 40public int getItemCount() { 41return list.size(); 42} 43 44class ViewHolder extends RecyclerView.ViewHolder{ 45private TextView text; 46 47public ViewHolder(View itemView) { 48super(itemView); 49text=(TextView)itemView.findViewById(android.R.id.text1); 50} 51} 52 }

3、在Activity中定义好控件以及数据加载操作
实现自定义RecyclerView中的数据加载事件监听,刷新、加载更多以及加载完成。
1 import android.app.ProgressDialog; 2 import android.os.Bundle; 3 import android.os.Handler; 4 import android.os.Message; 5 import android.support.v7.app.AppCompatActivity; 6 import android.support.v7.widget.LinearLayoutManager; 7 import android.widget.Toast; 8 9 import com.liuting.library.RefreshLoadMoreRecycleView; 10 import com.liuting.refreshloadmorelistview.adapter.RefreshLoadMoreRecycleAdapter; 11 12 import java.util.ArrayList; 13 import java.util.List; 14 15 public class MainActivity extends AppCompatActivity implements RefreshLoadMoreRecycleView.IOnScrollListener{ 16private RefreshLoadMoreRecycleView recycleView; //下拉刷新RecycleView 17private List< String> list; //列表 18private RefreshLoadMoreRecycleAdapter adapter; //Adapter 19private ProgressDialog dialog; //提示框 20private static final int REFRESH_Load=0; //下拉刷新 21private static final int MORE_Load=1; //加载更多 22private Handler handler =new Handler(){ 23@Override 24public void handleMessage(Message msg) { 25super.handleMessage(msg); 26switch (msg.what){ 27case REFRESH_Load: 28recycleView.setLoadMoreEnable(true); 29dismissDialog(); 30if(list!=null){ 31list.clear(); 32} 33loadData(); 34adapter.notifyDataSetChanged(); 35break; 36case MORE_Load: 37recycleView.setLoadMoreEnable(false); 38dismissDialog(); 39loadData(); 40adapter.notifyDataSetChanged(); 41break; 42} 43} 44}; 45 46@Override 47protected void onCreate(Bundle savedInstanceState) { 48super.onCreate(savedInstanceState); 49setContentView(R.layout.activity_main); 50initView(); 51} 52 53public void initView(){ 54dialog = new ProgressDialog(MainActivity.this); 55 56list=new ArrayList< > (); 57loadData(); 58recycleView = (RefreshLoadMoreRecycleView)findViewById(R.id.main_recycle_view_data); 59 60final LinearLayoutManager linearLayoutManager = new LinearLayoutManager(MainActivity.this); 61recycleView.setLayoutManager(linearLayoutManager); 63adapter = new RefreshLoadMoreRecycleAdapter(MainActivity.this,list); 64recycleView.setAdapter(adapter); 65recycleView.setListener(this); 66recycleView.setRefreshEnable(true); 67recycleView.setLoadMoreEnable(true); 68} 69 70/** 71* 加载数据 72*/ 73public void loadData(){ 74for(int i=0; i< 10; i++ ){ 75list.add("It is "+i); 76} 77} 78 79@Override 80public void onRefresh() { 81showDialog(); 82new Thread(){ 83@Override 84public void run() { 85super.run(); 86try { 87sleep(5000); 88handler.sendEmptyMessage(REFRESH_Load); 89} catch (InterruptedException e) { 90e.printStackTrace(); 91} 92} 93}.start(); 94} 95 96@Override 97public void onLoadMore() { 98showDialog(); 99new Thread(){ 100@Override 101public void run() { 102super.run(); 103try { 104sleep(5000); 105handler.sendEmptyMessage(MORE_Load); 106} catch (InterruptedException e) { 107e.printStackTrace(); 108} 109} 110}.start(); 111} 112 113@Override 114public void onLoaded() { 115Toast.makeText(MainActivity.this,"Loaded all",Toast.LENGTH_SHORT).show(); 116} 117 118/** 119* dismiss dialog 120*/ 121private void dismissDialog(){ 122if (dialog!=null& & dialog.isShowing()){ 123dialog.dismiss(); 124} 125} 126 127/** 128* show dialog 129*/ 130private void showDialog(){ 131if (dialog!=null& & !dialog.isShowing()){ 132dialog.show(); 133} 134} 135 }

 
三、最终效果图
Android之RecyclerView轻松实现下拉刷新和加载更多

文章图片

 
 
到这里就轻松实现了RecyclerView的下拉刷新和加载更多了。

    推荐阅读