打造一個萬能重新整理載入控制元件
序
最近幫一個老總搞一個物流專案,原本想著在這個經濟下滑的階段賺點外快也還不錯,結果在開發的過程中並非我開始想象的那麼輕鬆,物流專案的業務還是比較複雜的。什麼都不想多說了,先寫篇部落格壓壓驚。這次一起打造個萬能重新整理載入控制元件,其實剛接觸android的時候就有這個想法了,一直都沒有付諸行動,這段時間雖然比較累,但是閒暇時間還是將最初的想法實現的差不多了,可能大多數開發者和我一樣,每次用列表重新整理、載入的控制元件用的總不是那麼輕鬆,總是需要根據自己的業務需求來改動別人寫好的控制元件,還比如,用了別人的控制元件,突然又要在控制元件上加一個多的功能,這樣就相當比較耗時間了。
原理
我的想法是這樣的,最外層是一個BaseLayout extends LinearLayout,然後這個佈局的大小實際是超過螢幕的,最上面是HeaderView,最底下是FooterView,顧名思義,分別是用於載入和重新整理的,而螢幕部分顯示的ContentView,這個就是我們列表控制元件,當然了,隨著RecyclerView的出現,我們也就沒有必要實現ListView和GridView了,這樣更加方便使用。為了節約篇幅(寫篇文章也不容易,深入細節也沒有必要了),我們只聊聊重新整理,如何判斷是否要重新整理呢,首先使用者下拉的時候,螢幕上面的第一個Item必須是列表的第一個Item(因為列表控制元件都採用了複用機制),第二個條件是這個Item的最上面top是0,這個應該也很好理解,就是全暴露在螢幕中央,這樣,BaseLayout就可以攔截事件,利用Scroller來逐步的顯示HeaderView,直至滿足重新整理狀態。Ok,這個很簡單並不是我們的重點,當你上移BaseLayout,當HeaderView像圖二階段,你完全可以利用BaseLayout去攔截事件,那麼到了第三個步驟呢?難道還是攔截,那麼上移過程中FooterView肯定會暴露在螢幕中,這顯然不是我們想要的,所以,我們就是用巢狀滑動機制來解決這個問題,讓BaseLayout實現NestedScrollingParent,這樣當上滑階段也就是Push過程,我們在BaseLayout裡面監聽到ContentView的滑動過程,來實現我們的效果。用這樣的佈局方式,我的目的很明顯,就是想把重新整理和載入過程完全的解耦。並且,HeaderView 和 FooterView 以及ContentView 很輕鬆的替換,這樣就非常的方便,利於我們平時的開發。為了驗證我的想法是否可行,我從github上面隨便找了一個開源庫是對RecyclerView動過“手腳”的,是側滑Item刪除,然後效果還不錯,等會底下我顯示出效果圖。
效果
1.一共有兩種重新整理的方式,一種是根據臨界值改變狀態,一種是根據下來的距離來改變RefreshView的狀態(這裡就用美團的效果來參考下)。
2.載入的方式也提供了兩種風格,一種是快速下滑到底端,載入。另外一種是已經到了底端但是使用者還是拖動的,就採用了之前XListView的拖動載入方式。
3.出了載入更多的方式不同,另外提供了載入結束時,也就是資料全部載入完畢時的顯示效果,也有兩種方式。一種是直接底部顯示一個view,沒有更多資料,另外一種就類似QQ的重新整理效果,提示沒有更多,然後回彈回去。
4.另外還添加了Android-PullToRefresh的scroll over的效果。
5.當然,我們關心的實用價值,那麼當網路錯誤、或者載入失敗,效果該如何呢?NRecyclerView也提供了兩種方式,一個是沒有廣告位的,另外一種是有廣告位的。
從效果圖中也可以看到,不僅佔位還提供了重新整理功能,這是好多框架都沒有的。
6.NRecyclerView還提供了載入資料時不可滑動和可滑動的方式。
7.一般的載入方式,已經提供了差不多了,那麼至於RecyclerView的優勢當然是LayoutManager效果,我們看看不同LayoutManager載入圖片的效果如何把。
8.當然,上面都不是重點,很多第三方控制元件都能做到,我們NRecyclerView要做的是萬能載入控制元件,封裝了載入、重新整理的功能。比如,我要在重新整理、載入控制元件裡面新增一個側滑刪除的功能,這時,必須得我們自己修改原始碼了,但是NRecyclerView就很容易的解決了,這裡用SwipeMenuRecyclerView的控制元件,我也是隨便在github上找的。看看效果:
最後
寫一個重新整理載入控制元件是不是,但是能寫好也並非一件容易的事情,其中被bug折磨的死去活來的,可能NRecyclerView還存在一些bug,希望大家指明出來,我及時更新,後續時間多了,自然是對它拓展和做一些封裝和優化。當然有人願意和我一起維護、開發最好了,一起學習一起進步!