最近做一个自定义Behavior的需求,然后回过头来看了下嵌套滚动的流程。做个笔记记录下。
回顾下
View的事件机制是由父ViewGroup传递到子View的。这样的一个问题是无法处理同级子View的事件分发(特殊的手段可以实现,比如通过onTouchEvent强行传给另外一个View)。嵌套滚动机制的一个比较重要的封装是处理同级子View滚动效果。
嵌套滚动主要涉及到的两个接口是NestedScrollingChild和NestedScrollingParent,调用关系如下图。
dispatchNestedPreScroll是在onTouchEvent的ACTION_MOVE中执行的。public boolean dispatchNestedPreScroll(int dx, int dy, int[] consumed, int[] offsetInWindow)
在当前
View消耗之前(dispatchNestedScroll)会执行。可以用来阻止子View的消耗。consumed会赋值为滚动消耗的值(代表的是所有的子View滚动的距离的最大值),分别对应的是x、y的值。offsetInWindow相当于是View(当前View滚动的距离,比如是RecyclerView)滚动的距离。
dispatchNestedScroll是在onTouchEvent的ACTION_MOVE中执行的。public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed, int[] offsetInWindow)
开始分发滚动事件。offsetInWindow相当于是
View(当前View滚动的距离,比如是RecyclerView)滚动的距离。
CoordinatorLayout是很重要的一个关于嵌套滚动的类,里面海涉及到一个类Behavior。
- behavior 是什么:用来协调
CoordinatorLayout里面的元素。CoordinatorLayout里面的直接子View都可以使用Behavior来控制交互。 - 怎么设置:在xml中可以设置属性
app:layout_behavior(string),会通过反射创佳一个Behavior。<attr name="layout_behavior" format="string"/>