Android高级UI开发(二十三)自定义behavior(2)监听控件滑动

举报
yd_57386892 发表于 2020/12/28 23:50:06 2020/12/28
【摘要】 上一篇我们讲了自定义behavior监听控件的状态变化:例如垂直方向位移的变化。今天我们要谈的是如何监听控件的滑动事件。就是说当布局文件里有一个可滑动的控件(如RecyclerView、NestedScrollView、Viewpager页面里的NestedScrollView)滑动时,我们自定义的behavior可以帮观察者监听到该类事件,同时做相应的处理。我们还是从布局文...

上一篇我们讲了自定义behavior监听控件的状态变化:例如垂直方向位移的变化。今天我们要谈的是如何监听控件的滑动事件。就是说当布局文件里有一个可滑动的控件(如RecyclerView、NestedScrollView、Viewpager页面里的NestedScrollView)滑动时,我们自定义的behavior可以帮观察者监听到该类事件,同时做相应的处理。我们还是从布局文件讲起,在此之前先看以下运行效果:

 

1. 布局文件


  
  1. <android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
  2. xmlns:app="http://schemas.android.com/apk/res-auto"
  3. xmlns:tools="http://schemas.android.com/tools"
  4. android:layout_width="match_parent"
  5. android:layout_height="match_parent">
  6. <android.support.v4.widget.NestedScrollView
  7. android:id="@+id/nestedScroll"
  8. android:layout_width="200dp"
  9. android:layout_height="wrap_content"
  10. android:layout_gravity="left">
  11. <LinearLayout
  12. android:id="@+id/nestedScrollLayout"
  13. android:layout_width="match_parent"
  14. android:layout_height="wrap_content"
  15. android:orientation="vertical">
  16. <ImageView
  17. android:id="@+id/bt2"
  18. android:layout_margin="50dp"
  19. android:layout_width="100dp"
  20. android:layout_height="100dp"
  21. android:layout_gravity="left|top"
  22. android:background="@drawable/d1"
  23. android:textColor="@color/white" />
  24. <ImageView
  25. android:layout_margin="50dp"
  26. android:layout_width="100dp"
  27. android:layout_height="100dp"
  28. android:layout_gravity="left|top"
  29. android:background="@drawable/d2"
  30. android:textColor="@color/white" />
  31. <ImageView
  32. android:layout_margin="50dp"
  33. android:id="@+id/bt1"
  34. android:layout_width="100dp"
  35. android:layout_height="100dp"
  36. android:layout_gravity="left|top"
  37. android:background="@drawable/d2"
  38. android:textColor="@color/white" />
  39. <ImageView
  40. android:layout_margin="50dp"
  41. android:layout_width="100dp"
  42. android:layout_height="100dp"
  43. android:layout_gravity="left|top"
  44. android:background="@drawable/d2"
  45. android:textColor="@color/white" />
  46. <ImageView
  47. android:layout_margin="50dp"
  48. android:id="@+id/bt21"
  49. android:layout_width="100dp"
  50. android:layout_height="100dp"
  51. android:layout_gravity="left|top"
  52. android:background="@drawable/d2"
  53. android:tag="tv1"
  54. android:textColor="@color/white" />
  55. <ImageView
  56. android:layout_margin="50dp"
  57. android:id="@+id/bt23"
  58. android:layout_width="100dp"
  59. android:layout_height="100dp"
  60. android:layout_gravity="left|top"
  61. android:background="@drawable/d2"
  62. android:tag="tv1"
  63. android:textColor="@color/white" />
  64. </LinearLayout>
  65. </android.support.v4.widget.NestedScrollView>
  66. <ImageView
  67. android:background="@drawable/d1"
  68. android:id="@+id/obeserver"
  69. android:layout_marginRight="20dp"
  70. android:layout_width="72dp"
  71. android:layout_height="72dp"
  72. android:layout_gravity="right|center_vertical"
  73. android:text="观察者"
  74. app:layout_behavior="com.example.custombehavior.ListenerScrollBehavior" />
  75. </android.support.design.widget.CoordinatorLayout>

在这里我们声明一个被观测者NestedScrollView,再声明一个观察者NestedScrollView,同时为观察者配置一个自定义behavior:layout_behavior="com.example.custombehavior.ListenerScrollBehavior". 我们看到这个布局的根布局仍然是CoordinatorLayout,这与我们之前的一样,CoordinatorLayout布局捕捉到事件及控件状态变化后,分发给我们自定义的behavior。接下来我们就来看一下这个自定义behavior的实现,看它是如何来监听控件的滑动事件。

 

2. 自定义Behavior实现


  
  1. package com.example.custombehavior;
  2. import android.content.Context;
  3. import android.support.design.widget.CoordinatorLayout;
  4. import android.support.design.widget.CoordinatorLayout.Behavior;
  5. import android.support.v4.view.ViewCompat;
  6. import android.support.v4.widget.NestedScrollView;
  7. import android.util.AttributeSet;
  8. import android.util.Log;
  9. import android.view.View;
  10. import java.util.Random;
  11. public class ListenerScrollBehavior extends Behavior<View> {
  12. public ListenerScrollBehavior(Context arg0, AttributeSet arg1) {
  13. super(arg0, arg1);
  14. // TODO Auto-generated constructor stub
  15. }
  16. /**
  17. * 用来决定谁是观察者,谁是被观察者
  18. * @param coordinatorLayout ,父容器
  19. * @param child, 观察者
  20. @param directTargetChild,被观察者
  21. @param target: 与directTargetChild指的是同一个控件NestedScrollView
  22. */
  23. @Override
  24. public boolean onStartNestedScroll(CoordinatorLayout coordinatorLayout,
  25. View child, View directTargetChild, View target,
  26. int nestedScrollAxes) {
  27. // TODO Auto-generated method stub
  28. //监听垂直滚动
  29. return (nestedScrollAxes == ViewCompat.SCROLL_AXIS_VERTICAL)||super.onStartNestedScroll(coordinatorLayout, child, directTargetChild,
  30. target, nestedScrollAxes);
  31. }
  32. @Override
  33. public void onNestedPreScroll(CoordinatorLayout coordinatorLayout,
  34. View child, View target, int dx, int dy, int[] consumed) {
  35. // TODO Auto-generated method stub
  36. child.animate().rotation( dy* 360);
  37. super.onNestedPreScroll(coordinatorLayout, child, target, dx, dy, consumed);
  38. }
  39. @Override
  40. public boolean onNestedFling(CoordinatorLayout coordinatorLayout,
  41. View child, View target, float velocityX, float velocityY,
  42. boolean consumed) {
  43. return super.onNestedFling(coordinatorLayout, child, target, velocityX,
  44. velocityY, consumed);
  45. }
  46. }

这里和上一篇类似,只是重写的函数不一样,我们来介绍以下几个函数“

1.onStartNestedScroll(CoordinatorLayout coordinatorLayout, View child, View directTargetChild, View target, int nestedScrollAxes);

CoordinatorLayout :根布局

child:观察者

directTargetChild:被观察者

target:还是被观察者,在这里与directTargetChild指向的控件是同一个

nestedScrollAxes:将要监听的滚动方向,垂直还是水平。

child是观察者,对应布局里的id为observer控件 ;directTargetChild是被观察者,对应布局里的id为NestedScrollView控件。

nestedScrollAxes表示滚动的方向。在此我们return (nestedScrollAxes == ViewCompat.SCROLL_AXIS_VERTICAL)表示我们只监听NestedScrollView的垂直滑动事件。

2.onNestedPreScroll(CoordinatorLayout coordinatorLayout, View child, View target, int dx, int dy, int[] consumed)

当滑动时执行。

CoordinatorLayout :根布局

child:观察者

target:被观察者,在这里与directTargetChild指向的控件是同一个

nestedScrollAxes:将要监听的滚动方向,垂直还是水平。

dx:每次滚动的水平距离

dy:每次滚动的垂直距离

这里我们让观察者child执行动画:child.animate().rotation( dy* 360); 这样就实现了观察者监听到滑动事件并作出相应的处理。

3. onNestedFling(CoordinatorLayout coordinatorLayout, View child, View target, float velocityX, float velocityY, boolean consumed)

滚动的惯性。在这里我们没有用到,用于监听滚动的惯性,就是当人手指松开后列表还会滑动一段距离,我们可以检测到velocityX与velocityY两个惯性值,运用场景可以是:当滑动一个列表时,让另一个列表 跟着滑动,而且另一个列表的惯性值要与列表1的惯性值一样,才能真正保持同步滑动。

CoordinatorLayout :根布局

child:观察者

target:被观察者

velocityX  轴滚动的惯性值,就是人手指松开后列表还会滑动一段距离

velocityY  轴滚动的惯性值,就是人手指松开后列表还会滑动一段距离

consumed: 这个还不理解,望请指教。

 

OK,至此自定义Behavior监听滑动事件就讲到这里,最后附上源码地址:https://download.csdn.net/download/gaoxiaoweiandy/11009736

 

 

 
 

文章来源: blog.csdn.net,作者:冉航--小虾米,版权归原作者所有,如需转载,请联系作者。

原文链接:blog.csdn.net/gaoxiaoweiandy/article/details/88375509

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。