转载请标明出处:

http://blog.csdn.net/developer_jiangqq/article/details/49992269

本文出自:【江清清的博客】

(一).前言:

【好消息】个人网站已经上线运行,后面博客以及技术干货等精彩文章会同步更新,请大家关注收藏:http://www.lcode.org

话说RecyclerView已经面市很久,也在很多应用中得到广泛的使用,在整个开发者圈子里面也拥有很不错的口碑,那说明RecyclerView拥有比ListView,GridView之类控件有很多的优点,例如:数据绑定,Item View创建,View的回收以及重用等机制。前三三篇文章已经贡呢更新了以下三个部分:

  1. RecyclerView控件的基本使用,包括基础,进阶,高级部分,动画之类(点击进入)
  2. RecyclerView控件的实战实例(点击进入)
  3. RecyclerView控件集合AA(Android Annotations)注入框架实例(点击进入)

本来这个专题不打算更新,不过前两天看到各位童鞋还是挺积极的评论到,希望可以更新RecyclerView加入下拉刷新和上拉加载更多的功能。正好昨天周末,所以我这边也就实现了这样的功能,今天更新一下。具体代码已经上传到下面的项目中,欢迎各位去star和fork一下。

FastDev4Android框架项目地址:https://github.com/jiangqqlmj/FastDev4Android

RecyclerView实现的列表,默认情况下面是不带下拉刷新和上拉记载更多效果的,但是我在我们的实际项目当中,为了提高用户体验,这种效果一般都需要实现,在我以前的博客中已经重写了ListView(Android 列表下拉刷新组件PullToRefreshListView使用)实现上拉刷新和上拉加载更多效果。现在我们已经学会了ListView,GridView的替代品RecyclerView的基本使用方法,那么必不可少的也需要实现上拉刷新和上拉加载更多的效果了。今天我们会通过两种方式来实现,具体会采用Android的另一控件SwipeRefreshLayout。

(二).SwipeRefreshLayout介绍:

SwipeRefrshLayout是Google官方更新的一个Widget,可以实现下拉刷新的效果。该控件集成自ViewGroup在support-v4兼容包下,不过我们需要升级supportlibrary的版本到19.1以上。基本使用的方法如下:

  • setOnRefreshListener(OnRefreshListener):添加下拉刷新监听器
  • setRefreshing(boolean):显示或者隐藏刷新进度条
  • isRefreshing():检查是否处于刷新状态
  • setColorSchemeResources():设置进度条的颜色主题,最多设置四种,以前的setColorScheme()方法已经弃用了。

具体使用效果下面我们会看到。

(三).RecyclerView+SwpieRefreshLayout实现下拉刷新效果:

1.SwipeRefreshLayout本身自带下拉刷新的效果,那么我们可以选择在RecyclerView布局外部嵌套一层SwipeRefreshLayout布局即可,具体布局文件如下:

  1. <?xmlversionxmlversion="1.0" encoding="utf-8"?>
  2. <LinearLayoutxmlns:androidLinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"
  3. android:orientation="vertical"android:layout_width="match_parent"
  4. android:layout_height="match_parent">
  5. <includelayoutincludelayout="@layout/common_top_bar_layout"/>
  6. <android.support.v4.widget.SwipeRefreshLayout
  7. android:id="@+id/demo_swiperefreshlayout"
  8. android:layout_width="fill_parent"
  9. android:layout_height="fill_parent"
  10. android:scrollbars="vertical"
  11. >
  12. <android.support.v7.widget.RecyclerView
  13. android:id="@+id/demo_recycler"
  14. android:layout_width="fill_parent"
  15. android:layout_height="fill_parent"
  16. ></android.support.v7.widget.RecyclerView>
  17. </android.support.v4.widget.SwipeRefreshLayout>
  18. </LinearLayout>

2.接着在Activity中获取SwipeRefreshLayout控件并且设置OnRefreshListener监听器,同时实现里边的onRefresh()方法,在该方法中进行网络请求最新数据,然后刷新RecyclerView列表同时设置SwipeRefreshLayout的进度Bar的隐藏或者显示效果。具体代码如下:

  1. demo_swiperefreshlayout.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
  2. @Override
  3. public void onRefresh() {
  4. Log.d("zttjiangqq","invoke onRefresh...");
  5. new Handler().postDelayed(newRunnable() {
  6. @Override
  7. public void run() {
  8. List<String> newDatas = new ArrayList<String>();
  9. for (int i = 0; i <5; i++) {
  10. int index = i + 1;
  11. newDatas.add("new item" + index);
  12. }
  13. adapter.addItem(newDatas);
  14. demo_swiperefreshlayout.setRefreshing(false);
  15. Toast.makeText(RecyclerRefreshActivity.this, "更新了五条数据...", Toast.LENGTH_SHORT).show();
  16. }
  17. }, 5000);
  18. }
  19. });

3.除此之外我们也来看一下Adapter和Activity中的其他代码,也方便各位童鞋查看。

  1. RecyclerRefreshActivity.java
  2. public class RecyclerRefreshActivity extends BaseActivity {
  3. private LinearLayout top_bar_linear_back;
  4. private TextView top_bar_title;
  5. private SwipeRefreshLayout demo_swiperefreshlayout;
  6. private RecyclerView demo_recycler;
  7. private RefreshRecyclerAdapter adapter;
  8. private LinearLayoutManager linearLayoutManager;
  9. private int lastVisibleItem;
  10. @Override
  11. protected void onCreate(BundlesavedInstanceState) {
  12. super.onCreate(savedInstanceState);
  13. setContentView(R.layout.recycler_refresh_layout);
  14. top_bar_linear_back=(LinearLayout)this.findViewById(R.id.top_bar_linear_back);
  15. top_bar_linear_back.setOnClickListener(new CustomOnClickListener());
  16. top_bar_title=(TextView)this.findViewById(R.id.top_bar_title);
  17. top_bar_title.setText("RecyclerView下拉刷新,下拉加载更多...");
  18. demo_swiperefreshlayout=(SwipeRefreshLayout)this.findViewById(R.id.demo_swiperefreshlayout);
  19. demo_recycler=(RecyclerView)this.findViewById(R.id.demo_recycler);
  20. //设置刷新时动画的颜色,可以设置4个
  21. demo_swiperefreshlayout.setProgressBackgroundColorSchemeResource(android.R.color.white);
  22. demo_swiperefreshlayout.setColorSchemeResources(android.R.color.holo_blue_light,
  23. android.R.color.holo_red_light,android.R.color.holo_orange_light,
  24. android.R.color.holo_green_light);
  25. demo_swiperefreshlayout.setProgressViewOffset(false, 0, (int) TypedValue
  26. .applyDimension(TypedValue.COMPLEX_UNIT_DIP, 24, getResources()
  27. .getDisplayMetrics()));
  28. linearLayoutManager=new LinearLayoutManager(this);
  29. linearLayoutManager.setOrientation(OrientationHelper.VERTICAL);
  30. demo_recycler.setLayoutManager(linearLayoutManager);
  31. //添加分隔线
  32. demo_recycler.addItemDecoration(new AdvanceDecoration(this, OrientationHelper.VERTICAL));
  33. demo_recycler.setAdapter(adapter = new RefreshRecyclerAdapter(this));
  34. demo_swiperefreshlayout.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
  35. @Override
  36. public void onRefresh() {
  37. Log.d("zttjiangqq","invoke onRefresh...");
  38. new Handler().postDelayed(newRunnable() {
  39. @Override
  40. public void run() {
  41. List<String> newDatas = new ArrayList<String>();
  42. for (int i = 0; i <5; i++) {
  43. int index = i + 1;
  44. newDatas.add("new item" + index);
  45. }
  46. adapter.addItem(newDatas);
  47. demo_swiperefreshlayout.setRefreshing(false);
  48. Toast.makeText(RecyclerRefreshActivity.this, "更新了五条数据...", Toast.LENGTH_SHORT).show();
  49. }
  50. }, 5000);
  51. }
  52. });
  53. class CustomOnClickListenerimplements View.OnClickListener{
  54. @Override
  55. public void onClick(View v) {
  56. RecyclerRefreshActivity.this.finish();
  57. }
  58. }
  59. }
  1. RefreshRecyclerAdapter.java
  2. public class RefreshRecyclerAdapter extends RecyclerView.Adapter<RefreshRecyclerAdapter.ViewHolder>{
  3. private LayoutInflater mInflater;
  4. private List<String> mTitles=null;
  5. public RefreshRecyclerAdapter(Context context){
  6. this.mInflater=LayoutInflater.from(context);
  7. this.mTitles=new ArrayList<String>();
  8. for (int i=0;i<20;i++){
  9. int index=i+1;
  10. mTitles.add("item"+index);
  11. }
  12. }
  13. /**
  14. * item显示类型
  15. * @param parent
  16. * @param viewType
  17. * @return
  18. */
  19. @Override
  20. public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
  21. final Viewview=mInflater.inflate(R.layout.item_recycler_layout,parent,false);
  22. //这边可以做一些属性设置,甚至事件监听绑定
  23. //view.setBackgroundColor(Color.RED);
  24. ViewHolder viewHolder=new ViewHolder(view);
  25. return viewHolder;
  26. }
  27. /**
  28. * 数据的绑定显示
  29. * @param holder
  30. * @param position
  31. */
  32. @Override
  33. public void onBindViewHolder(ViewHolder holder, int position) {
  34. holder.item_tv.setText(mTitles.get(position));
  35. holder.itemView.setTag(position);
  36. }
  37. @Override
  38. public int getItemCount() {
  39. return mTitles.size();
  40. }
  41. //自定义的ViewHolder,持有每个Item的的所有界面元素
  42. public static class ViewHolder extends RecyclerView.ViewHolder {
  43. public TextView item_tv;
  44. public ViewHolder(View view){
  45. super(view);
  46. item_tv = (TextView)view.findViewById(R.id.item_tv);
  47. }
  48. }
  49. //添加数据
  50. public void addItem(List<String> newDatas) {
  51. //mTitles.add(position, data);
  52. //notifyItemInserted(position);
  53. newDatas.addAll(mTitles);
  54. mTitles.removeAll(mTitles);
  55. mTitles.addAll(newDatas);
  56. notifyDataSetChanged();
  57. }
  58. public void addMoreItem(List<String> newDatas) {
  59. mTitles.addAll(newDatas);
  60. notifyDataSetChanged();
  61. }
  62. }

以上重要地方的注释已经加上去了。

5.运行效果如下:

(四).RecyclerView设置滚动事件加入上拉加载更多功能

下面我们再来看RecyclerView和相关类的一些特性,

LayoutManger给我们提供了以下几个方法来让开发者方便的获取到屏幕上面的顶部item和顶部item相关的信息:

  • findFirstVisibleItemPosition()
  • findFirstCompletlyVisibleItemPosition()
  • findLastVisibleItemPosition()
  • findLastCompletlyVisibleItemPosition()

同时通过Recycler.Adapter的getItemCount()方法可以轻松获取到RecyclerView列表中Item View的个数。

那么下面我们通过监听滑动(滚动)事件,然后在里边判断是否已经滑动到最底部来加载更多的数据,使用方法如下:

  1. //RecyclerView滑动监听
  2. demo_recycler.setOnScrollListener(new RecyclerView.OnScrollListener() {
  3. @Override
  4. public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
  5. super.onScrollStateChanged(recyclerView, newState);
  6. if (newState ==RecyclerView.SCROLL_STATE_IDLE && lastVisibleItem + 1 ==adapter.getItemCount()) {
  7. new Handler().postDelayed(new Runnable() {
  8. @Override
  9. public void run() {
  10. List<String> newDatas = new ArrayList<String>();
  11. for (int i = 0; i< 5; i++) {
  12. int index = i +1;
  13. newDatas.add("more item" + index);
  14. }
  15. adapter.addMoreItem(newDatas);
  16. }
  17. },1000);
  18. }
  19. }
  20. @Override
  21. public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
  22. super.onScrolled(recyclerView,dx, dy);
  23. lastVisibleItem =linearLayoutManager.findLastVisibleItemPosition();
  24. }
  25. });

运行效果如下:

(五).升级RecyclerView加入FootView实现上拉加载

上面我们虽然已经实现了上拉加载更多的效果,但是还比较丑陋,最起码要让用户知道确实在上拉加载的过程吧,例如加载一个底部的进度布局。这样一想,那么我们就按照ListView方式addFootView()呗,不过很可惜的是RecyclerView没有给我们提供addFootView()方法,那该怎么样办呢?我们来看RecyclerView.Apapter类:

我们要实现一个自定义Adapter一定需要实现onCreateViewHolder(ViewGroup paren,int viewType)方法,注意看方法中的第二个参数viewType,是不是想到布局类型了,也就是说该也支持多套布局显示的,那么查看基类中的所有方法如下:

上面有一个方法getItemType(),这个就和ListView的Adapter的实现差不多了,那么我们这边可以使用多套布局给RecyclerView加入一个FootView布局即可。RefreshFootAdapter.java具体实现流程如下:

1.加入布局状态标志-用来判断此时加载是普通Item还是foot view:

private static final int TYPE_ITEM =0;  //普通Item View

private static final intTYPE_FOOTER = 1;  //顶部FootView

2.重写getItemCount()方法,返回的Item数量在数据的基础上面+1,增加一项FootView布局项

  1. public intgetItemCount() {
  2. return mTitles.size()+1;
  3. }

3.重写getItemViewType方法来判断返回加载的布局的类型

  1. public int getItemViewType(int position) {
  2. // 最后一个item设置为footerView
  3. if (position + 1 == getItemCount()) {
  4. return TYPE_FOOTER;
  5. } else {
  6. return TYPE_ITEM;
  7. }
  8. }

4.接着onCreateViewHolder(ViewGroup parent,int viewType)加载布局的时候根据viewType的类型来选择指定的布局创建,返回即可:

  1. public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
  2. //进行判断显示类型,来创建返回不同的View
  3. if(viewType==TYPE_ITEM){
  4. Viewview=mInflater.inflate(R.layout.item_recycler_layout,parent,false);
  5. //这边可以做一些属性设置,甚至事件监听绑定
  6. //view.setBackgroundColor(Color.RED);
  7. ItemViewHolder itemViewHolder=new ItemViewHolder(view);
  8. return itemViewHolder;
  9. }else if(viewType==TYPE_FOOTER){
  10. Viewfoot_view=mInflater.inflate(R.layout.recycler_load_more_layout,parent,false);
  11. //这边可以做一些属性设置,甚至事件监听绑定
  12. //view.setBackgroundColor(Color.RED);
  13. FootViewHolder footViewHolder=new FootViewHolder(foot_view);
  14. return footViewHolder;
  15. }
  16. return null;
  17. }

5.最后进行判断数据的时候(onBindViewHolder),判断holder的类型来进行判定数据即可.

  1. public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
  2. if(holder instanceof ItemViewHolder) {
  3. ((ItemViewHolder)holder).item_tv.setText(mTitles.get(position));
  4. holder.itemView.setTag(position);
  5. }else if(holder instanceof FootViewHolder){
  6. FootViewHolderfootViewHolder=(FootViewHolder)holder;
  7. switch (load_more_status){
  8. case PULLUP_LOAD_MORE:
  9. footViewHolder.foot_view_item_tv.setText("上拉加载更多...");
  10. break;
  11. case LOADING_MORE:
  12. footViewHolder.foot_view_item_tv.setText("正在加载更多数据...");
  13. break;
  14. }
  15. }
  16. }

6.整个RefreshFootAdapter完整代码如下:

  1. packagecom.chinaztt.fda.adapter;
  2. public class RefreshFootAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder>{
  3. //上拉加载更多
  4. public static final int  PULLUP_LOAD_MORE=0;
  5. //正在加载中
  6. public static final int  LOADING_MORE=1;
  7. //上拉加载更多状态-默认为0
  8. private int load_more_status=0;
  9. private LayoutInflater mInflater;
  10. private List<String> mTitles=null;
  11. private static final intTYPE_ITEM = 0;  //普通Item View
  12. private static final intTYPE_FOOTER = 1;  //顶部FootView
  13. public RefreshFootAdapter(Context context){
  14. this.mInflater=LayoutInflater.from(context);
  15. this.mTitles=new ArrayList<String>();
  16. for (int i=0;i<20;i++){
  17. int index=i+1;
  18. mTitles.add("item"+index);
  19. }
  20. }
  21. /**
  22. * item显示类型
  23. * @param parent
  24. * @param viewType
  25. * @return
  26. */
  27. public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
  28. //进行判断显示类型,来创建返回不同的View
  29. if(viewType==TYPE_ITEM){
  30. Viewview=mInflater.inflate(R.layout.item_recycler_layout,parent,false);
  31. //这边可以做一些属性设置,甚至事件监听绑定
  32. //view.setBackgroundColor(Color.RED);
  33. ItemViewHolder itemViewHolder=new ItemViewHolder(view);
  34. return itemViewHolder;
  35. }else if(viewType==TYPE_FOOTER){
  36. Viewfoot_view=mInflater.inflate(R.layout.recycler_load_more_layout,parent,false);
  37. //这边可以做一些属性设置,甚至事件监听绑定
  38. //view.setBackgroundColor(Color.RED);
  39. FootViewHolder footViewHolder=new FootViewHolder(foot_view);
  40. return footViewHolder;
  41. }
  42. return null;
  43. }
  44. /**
  45. * 数据的绑定显示
  46. * @param holder
  47. * @param position
  48. */
  49. public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
  50. if(holder instanceof ItemViewHolder) {
  51. ((ItemViewHolder)holder).item_tv.setText(mTitles.get(position));
  52. holder.itemView.setTag(position);
  53. }else if(holder instanceof FootViewHolder){
  54. FootViewHolder footViewHolder=(FootViewHolder)holder;
  55. switch (load_more_status){
  56. case PULLUP_LOAD_MORE:
  57. footViewHolder.foot_view_item_tv.setText("上拉加载更多...");
  58. break;
  59. case LOADING_MORE:
  60. footViewHolder.foot_view_item_tv.setText("正在加载更多数据...");
  61. break;
  62. }
  63. }
  64. }
  65. /**
  66. * 进行判断是普通Item视图还是FootView视图
  67. * @param position
  68. * @return
  69. */
  70. @Override
  71. public int getItemViewType(int position) {
  72. // 最后一个item设置为footerView
  73. if (position + 1 == getItemCount()) {
  74. return TYPE_FOOTER;
  75. } else {
  76. return TYPE_ITEM;
  77. }
  78. }
  79. @Override
  80. public int getItemCount() {
  81. return mTitles.size()+1;
  82. }
  83. //自定义的ViewHolder,持有每个Item的的所有界面元素
  84. public static class ItemViewHolder extends RecyclerView.ViewHolder {
  85. public TextView item_tv;
  86. public ItemViewHolder(View view){
  87. super(view);
  88. item_tv = (TextView)view.findViewById(R.id.item_tv);
  89. }
  90. }
  91. /**
  92. * 底部FootView布局
  93. */
  94. public static class FootViewHolder extends  RecyclerView.ViewHolder{
  95. private TextView foot_view_item_tv;
  96. public FootViewHolder(View view) {
  97. super(view);
  98. foot_view_item_tv=(TextView)view.findViewById(R.id.foot_view_item_tv);
  99. }
  100. }
  101. //添加数据
  102. public void addItem(List<String> newDatas) {
  103. //mTitles.add(position, data);
  104. //notifyItemInserted(position);
  105. newDatas.addAll(mTitles);
  106. mTitles.removeAll(mTitles);
  107. mTitles.addAll(newDatas);
  108. notifyDataSetChanged();
  109. }
  110. public void addMoreItem(List<String> newDatas) {
  111. mTitles.addAll(newDatas);
  112. notifyDataSetChanged();
  113. }
  114. /**
  115. * //上拉加载更多
  116. * PULLUP_LOAD_MORE=0;
  117. * //正在加载中
  118. * LOADING_MORE=1;
  119. * //加载完成已经没有更多数据了
  120. * NO_MORE_DATA=2;
  121. * @param status
  122. */
  123. public void changeMoreStatus(int status){
  124. load_more_status=status;
  125. notifyDataSetChanged();
  126. }
  127. }

同时该Adaper中我还定义一个changeMoreStatus()方法和两个字符串常量可以来进行修改FootView中字符串提醒文本的。

7.整体Activity中还是设置监听RecyclerView的滚动事件.代码和第一个例子差不多,不过RecyclerView需要设置这边的Adapter了,demo_recycler.setAdapter(adapter= new RefreshFootAdapter(this));

  1. demo_recycler.setOnScrollListener(new RecyclerView.OnScrollListener() {
  2. @Override
  3. public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
  4. super.onScrollStateChanged(recyclerView, newState);
  5. if (newState ==RecyclerView.SCROLL_STATE_IDLE && lastVisibleItem + 1 ==adapter.getItemCount()) {
  6. adapter.changeMoreStatus(RefreshFootAdapter.LOADING_MORE);
  7. newHandler().postDelayed(new Runnable() {
  8. @Override
  9. public void run() {
  10. List<String> newDatas = new ArrayList<String>();
  11. for (int i = 0; i< 5; i++) {
  12. int index = i +1;
  13. newDatas.add("more item" + index);
  14. }
  15. adapter.addMoreItem(newDatas);
  16. adapter.changeMoreStatus(RefreshFootAdapter.PULLUP_LOAD_MORE);
  17. }
  18. }, 2500);
  19. }
  20. }
  21. @Override
  22. public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
  23. super.onScrolled(recyclerView,dx, dy);
  24. lastVisibleItem =linearLayoutManager.findLastVisibleItemPosition();
  25. }
  26. });

查看代码之后,大家肯定也发现在onScrollStateChanged()方法中,Adapter.addMoreItem()和Adapter.changeMoreStatus()方法内部都调用了notifyDataSetChanged()方法,也就是说这边刷新了两次,针对这个问题,大家可以把第二个方法放入到addMoreItem()内部去,调用一次刷新操作接口。同时也可以自己按照实际需求进行优化。

8.运行效果如下:

(六).最后总结

今天我们通过SwipeRefreshLayout和RecyclerView结合以及改造Adapter方式实现了RecyclerView的下拉刷新和上拉加载更多的效果。

本次具体实例注释过的全部代码已经上传到FastDev4Android项目中了。同时欢迎大家去Github站点进行clone或者下载浏览:

https://github.com/jiangqqlmj/FastDev4Android 同时欢迎大家star和fork整个开源快速开发框架项目~

本人录制AA(Android Annotations)注入框架的视频教程已经上线了,欢迎大家前往观看。http://www.cniao5.com/course/10074

尊重原创,转载请注明:From Sky丶清(http://blog.csdn.net/developer_jiangqq) 侵权必究!

实现上拉加载更多的SwipeRefreshLayout的更多相关文章

  1. SwipeRefreshLayout详解和自定义上拉加载更多

    个人主页 演示Demo下载 本文重点介绍了SwipeRefreshLayout的使用和自定View继承SwipeRefreshLayout添加上拉加载更多的功能. 介绍之前,先来看一下SwipeRef ...

  2. RecyclerView实例-实现可下拉刷新上拉加载更多并可切换线性流和瀑布流模式(1)

    摘要 最近项目有个列表页需要实现线性列表和瀑布流展示的切换,首先我想到的就是上 [RecyclerView],他本身已经很好的提供了三种布局方式,只是简单做个切换应该是很简单的事情,如果要用Recyc ...

  3. google官方的下拉刷新+自定义上拉加载更多

    转载请标注转载:http://blog.csdn.net/oqihaogongyuan/article/details/50949118 google官方的下拉刷新+自定义上拉加载更多 现在很多app ...

  4. Android 开发 上拉加载更多功能实现

    实现思维 开始之前先废话几句,Android系统没有提供上拉加载的控件,只提供了下拉刷新的SwipeRefreshLayout控件.这个控件我们就不废话,无法实现上拉刷新的功能.现在我们说说上拉加载更 ...

  5. RecyclerView下拉刷新上拉加载更多

    现在Android里都建议用RecyclerView代替ListView和GridView,所以下拉刷新和上拉加载更多也需要实现.下拉刷新可以用SwipeRefreshLayout 包裹Recycle ...

  6. YCRefreshView-自定义支持上拉加载更多,下拉刷新。。。

    自定义支持上拉加载更多,下拉刷新,支持自由切换状态[加载中,加载成功,加载失败,没网络等状态]的控件,拓展功能[支持长按拖拽,侧滑删除]可以选择性添加 .具体使用方法,可以直接参考demo. 轻量级侧 ...

  7. 原生js移动端touch事件实现上拉加载更多

    大家都知道jQuery里没有touch事件,所以在移动端使用原生js实现上拉加载效果还是很不错的,闲话不多说,代码如下: //获取要操作的元素 var objSection = document.ge ...

  8. H5基于iScroll实现下拉刷新,上拉加载更多

    前言 前一段有个手机端的项目需要用到下拉刷新和上拉加载更多的效果,脑海里第一反映就是微博那种效果,刚开始的理解有些偏差,以为下拉也是追加数据,上拉也是追加数据,后请教同事后发现其实下拉只是刷新最新数据 ...

  9. 常见开发需求之angular上拉加载更多

    需求   移动端使用angular实现上拉加载更多的条目,这个需求比较常见,网上的插件改动起来比较麻烦,不如自己写一个最适合,以前有同事写了一个,奈何bug太多,后来改分页了,我们产品说什么都让做,没 ...

随机推荐

  1. PHP用socket连接SMTP服务器发送邮件

    PHP用socket连接SMTP服务器发送邮件 PHP用socket连接SMTP服务器发送邮件学习实验记录: 分析与SMTP会话的一般流程 1. HELO XXX \r\n //XXX就是自己起个名字 ...

  2. JavaScript 倒计时器,闹钟功能

    <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title> ...

  3. 3. Vue-router 路由

    路由是根据不同的url地址展现不同的内容或页面. 前端路由就是把不同路由对应不同的内容或页面的任务交给前端来做(在单页面应用,大部分页面结构不变,只改变部分内容的使用),之前是通过服务器根据url的不 ...

  4. [selenium]选取下拉框内容的方法

    说明:本文章主要是对select元素操作的讲解,非select元素的下拉框需要另外分析 1.select元素示例: 2.select下拉框选取的3种方法 WebElement selector = d ...

  5. MySQL和SqlServer的区别

    一.查看表结构数量等mysql语句: -- 查看系统内所有数据库 show databases: -- 查询数据库内所有表 show tables; -- 显示表结构 desc 表名; sql ser ...

  6. 小贝_redis web管理界面工具安装

    RedisWEB管理界面工具安装 一.概述 二.文件下载 三.安装过程 一.概述 1.因为redis是基于C/S的方式开发.也就是说,仅仅要满足于redis的client通信要求的,都能够作为redi ...

  7. vue中监听路由参数变化

    今天遇到一个这样的业务场景:在同一个路由下,只改变路由后面的参数值, 比如在这个页面  /aaa?id=1 ,在这个页面中点击一个按钮后 跳转到 /aaa?id=2 , 但从“/aaa?id=1”到“ ...

  8. (转)linux的一个find命令配合rm删除某天前的文件

    转自:http://www.cnblogs.com/mingforyou/p/3930624.html 语句写法:find 对应目录 -mtime +天数 -name "文件名"  ...

  9. jQuery实现多种切换效果的图片切换的五款插件

    1:Nivo SliderNivoslider:丰富的图片切换效果 官方网址:https://themeisle.com/plugins/nivo-slider 查看演示:https://www.he ...

  10. Latex表格制作记录

    Latex表格制作记录 主要功能 合并表格的行列 长表格的使用 makecell例程借鉴 效果图 参考代码 \documentclass{ctexart} \usepackage{indentfirs ...