DEVLOG 9.10 關(guān)于ViewDragHelper的使用小結(jié)
Q:為什么要使用ViewDragHelper?
A: 為了簡化ViewGroup中一些復(fù)雜的拖拽邏輯.

ViewDragHelper中的重要概念
ViewDragHelper.Callback?????
我們一般通過這個(gè)回調(diào)來控制View在被拖動(dòng)時(shí)的行為。它主要包含這些回調(diào)方法:

2. 使用ViewDragHelper【接管】onInterceptTouchEvent和onTouchEvent方法。
在接管這些方法的時(shí)候,上述回調(diào)中有些方法必須重寫。


因?yàn)槲覀兺ǔJ褂肰iewDragHelper的返回值作為onInterceptTouchEvent的返回值,所以我們并不清楚這個(gè)ViewGroup是否真正攔截了事件流??紤]最簡單的情形,如果我們的ViewGroup中只有一個(gè)View。

ViewDragHelper對(duì)于Down事件只做了簡單的處理,對(duì)于MOVE事件,ViewDragHelper會(huì)檢查【滑動(dòng)范圍】。這個(gè)只是做一個(gè)限制性的操作。這個(gè)通過ViewHorizontalDragRange和VerticalDragRange確定。
clampViewPositionHorizontal和Vertical方法確定滑動(dòng)時(shí)的位置。如果只設(shè)置水平滑動(dòng),Vertical返回0。同時(shí)可以檢查當(dāng)前的滑動(dòng)是否到了邊界,如果到了邊界,通過設(shè)置一個(gè)固定值,可以避免出界。
2. 滑動(dòng)邊界
ViewDragHelper可以檢查在邊界位置的滑動(dòng)

這里有很多不同的枚舉,檢查在不同邊緣的滑動(dòng)。
3. onViewReleased
通過這個(gè)回調(diào)可以實(shí)現(xiàn)如微信電話的icon回彈的效果。舉個(gè)例子:

如果超過中點(diǎn)就會(huì)強(qiáng)制回到左邊界或者右邊界,通過settleCapturedViewAt。他的具體實(shí)現(xiàn)使用了Scroller,我們知道使用Scroller就必須要重寫computeScroll,而且使用scroller.startScroll也必須使用View#invalidate。具體的原因我們可以看看:

因?yàn)閂iewDragHelper最終使用了Scroller實(shí)現(xiàn)滑動(dòng),而Scoller本身并不能滑動(dòng),他只是一個(gè)計(jì)算器,根據(jù)時(shí)間的流逝計(jì)算應(yīng)該滑動(dòng)到的位置。真正的滑動(dòng)邏輯是在View調(diào)用invalidate之后,View在繪制過程中會(huì)索取scrollX scrollY,然后做一個(gè)小位移。
我們需要實(shí)現(xiàn)computeScroll,主要是為了判定滑動(dòng)是否到了盡頭。
