Android 自定義View UC下拉重新整理效果(二)

joe發表於2016-11-10

啦啦啦,這是山寨UC瀏覽器的下拉重新整理效果的第二篇,第一篇請移步Android 自定義View UC下拉重新整理效果(一)

我們看圖說話:

Android 自定義View UC下拉重新整理效果(二)

pull_refresh2.gif

主要工作

1.下拉重新整理的圓形向回首頁的圓形的過度以及返回的效果。
2.View的事件分發等等。
3.相關介面回撥。

對於第一塊,就是這個切換是的效果,其實在Android drawPath實現QQ拖拽泡泡我的第一篇文章中就講了,主要就是使用貝塞爾曲線來實現的。

只是這裡我試著使用了四階的貝塞爾曲線,因為控制點如果就一個的話,看起來有時候會覺得那個弧度拉得特別的尖,一點都不好看,而且我山寨的這個效果也沒有UC的那個那麼帥氣,可能還需要做相關的改進,如果你有好的點子請記得給我留言,一起完善嘛!!

這裡兩個控制點的偏移量是寫死的,而不是根據圓形的size的百分比計算出來的,所以如果你修改了圓形的半徑,那麼這裡可能會出現小小的問題,需要手動完善下!

下拉重新整理

其實現在的下拉重新整理也是爛大街的,就我現在理解的下拉重新整理其實有兩種模式了,一種是之前的寫好一個頭佈局在那個HeaderLayout中,然後margin將其隱藏掉,然後在下拉的時候攔截相關事件,決定是否應該讓Header顯示出來。攔截的條件就是子View(ListView ScrollView RecycleView等等是否在頂部了而且手勢是向下拉(dy

今天我們不說這種下拉,而是介紹Google在Android5.0(希望我沒有記錯 )提供的巢狀滑動的新機制

向下相容的問題

從API21(就是5.0開始),ViewParent的介面裡面多了onStartNestedScroll()onStopNestedScroll()等等的方法!當然,對應的ViewGroup中也有了這些方法,目測是空實現,因為它實現了這個介面嘛。那麼問題來了,如果你要向下相容腫麼辦呢?!
這裡有supportV4包來提供向下相容,不會寫不懂這玩意兒不著急,想想Android新的控制元件(RecycleView SwipeRefreshLayout NestedScrollView)這些都是支援巢狀滑動滴。。

相關介面方法

NestedScrollingParentNestedScrollingChild這兩個介面就是用來實現相關的向下相容的方法滴。。

This interface should be implemented by ViewGroup subclasses that wish to support scrolling operations delegated by a nested child view.
Classes implementing this interface should create a final instance of a NestedScrollingParentHelper as a field and delegate any View or ViewGroup methods to the NestedScrollingParentHelper methods of the same signature.
Views invoking nested scrolling functionality should always do so from the relevant ViewCompat, ViewGroupCompat or ViewParentCompat compatibility shim static methods. This ensures interoperability with nested scrolling views on Android 5.0 Lollipop and newer.

這個是NestedScrollingParent自己的一番解釋,可以明確知道,在5.0或者更新的,什麼ViewCompat等就提供了相關支援了(這個就是前面我說的那個嘛!),然後相容的話,就要用這個,而且還要使用一個叫NestedScrollingParentHelper的輔助類來統一處理一些東西。

Android 自定義View UC下拉重新整理效果(二)

NestedScrollingParent相關的方法.png

Android 自定義View UC下拉重新整理效果(二)

NestedScrollingChild的相關方法.png

然後是不是感覺要嗶了狗了,這麼多方法要實現?!其實我也是醉醉的,然後打算抄抄別人的就好了!

然後各種實現的方法中:

新的巢狀滑動的分發機制:

所以說並不是很複雜,其實就是在以前的事件分發的基礎上給父View提供了一個消費事件的機會,以前的話,誰接受了DOWN事件,那麼之後所有的事件都會交給它處理,直到它不處理的時候才會又依次返回給父View,或者直到新的DOWN事件開始分發。

巢狀滑動的意思就是在子View處理相關事件的時候,可以根據情況反饋給父View,然後根據父View處理的結果再進行下一步的處理!

RecycleView實現了NestedScrollingChild,在TouchEvet()中有以下邏輯:

根據上面的程式碼可以看出onNestedPreScroll(),這個就是在子View還沒有滑動之前會先走的,如果父View有相關消費,那麼子View會計算出父View消費的偏移量,繼續消費剩餘的偏移量。而在子View的消費的過程中,它會計算出過程中並沒有消費的偏移量。

然後回撥dispatchNestedScroll,父View就可以在onNestedScroll()中進行處理了!

最後在UP或者CANCLE事件中,子View會stopNestedScroll(),然後父View就走到了onStopNestedScroll()。整個巢狀滑動到此結束!

具體實現

1.下拉的時候展現頭佈局
這裡其實就是走onNestedScroll(),因為這個時候子View已經在頂部了,向下拉的dy偏移量它肯定消費不了,所以在onNestedScroll()中unconsumedY就是父View需要消費的。
2.下拉的過程中又開始向上滑動
這裡就需要注意了,這個時候,父View和子View都可以響應和消費對應的事件的,因為他們現在都是可以向上滑動的,但是這裡必須要父View優先消費事件,所以這裡就要在onNestedPreScroll()中做相關的處理。

OK,到這裡,巢狀滑動就基本好了!接下來就是控制頭佈局的展現了!這裡就是直接讓子View向下移動,頭佈局自然就出現了!然後將相關偏移量傳到之前的TouchCircleView中,完成相關動畫!

相關方法及回撥

相關Demo請移步我的github。。。

打賞支援我寫出更多好文章,謝謝!

打賞作者

打賞支援我寫出更多好文章,謝謝!

任選一種支付方式

Android 自定義View UC下拉重新整理效果(二) Android 自定義View UC下拉重新整理效果(二)

相關文章