文章首發:Android程序員日記javascript
做者:賢榆的魚java
測試閱讀時間:4min 30sandroid
我先把昨天那篇「仿掘金框架之listview全解(一)」中提到的,咱們能夠經過這個項目練習到的知識點再列舉一下:git
listView的基本用法程序員
listView的複用優化github
listview添加headerView實現一些佈局和功能segmentfault
listview經過footerview和滾動監聽實現上拉加載更多app
listview經過觸摸監聽事件實現上下bar的佈局隱藏功能框架
在昨天的分享當中,我已經分享了前面四點!那麼今天我接着分享第五點,很少說先看掘金app自己的動態效果圖ide
思路:在listView的觸摸事件當中,咱們判斷手觸摸滑動大於必定的正值或者小於必定的負值,咱們分別對應進行頭尾bar的隱藏和顯示的屬性動畫!
Step 0:先展現一下總體的佈局
處理技巧:爲了可以在隱藏以後全屏都是listview那麼咱們須要用RelativeLayout做爲根佈局,讓listview在底層,頭尾bar在上層!同時爲了避免讓headbar遮擋住headerView的內容,因此咱們再作添加一塊headbar高度的空白view!
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" tools:context="com.timen4.ronnny.JueJinModel.MainActivity"> <android.support.v4.widget.SwipeRefreshLayout android:id="@+id/sr_refresh" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_weight="1" > <ListView android:scrollbars="vertical" android:fadingEdge="vertical" android:overScrollMode="never" android:dividerHeight="0.5dp" android:divider="#05999999" android:layout_width="match_parent" android:layout_height="wrap_content" android:id="@+id/listView" android:layout_alignParentTop="true" /> <Button android:clickable="true" android:visibility="gone" android:id="@+id/empty_fresh" android:layout_width="match_parent" android:layout_height="match_parent" android:text="暫無數據點擊刷新" android:textSize="40sp" /> </android.support.v4.widget.SwipeRefreshLayout> <LinearLayout android:visibility="visible" android:clickable="true" android:background="#0280FC" android:gravity="center_vertical" android:id="@+id/head_bar" android:layout_width="match_parent" android:layout_height="50dp" android:orientation="horizontal"> <Button android:drawableLeft="@drawable/tab_home_find_search" android:paddingLeft="8dp" android:drawablePadding="8dp" android:layout_margin="7dp" android:background="@drawable/search_button_selector" android:textColor="#99ffffff" android:text="@string/search" android:gravity="left|center_vertical" android:layout_width="match_parent" android:layout_height="wrap_content" /> </LinearLayout> <LinearLayout android:gravity="bottom" android:background="@drawable/shadow_bottom" android:layout_alignParentBottom="true" android:orientation="horizontal" android:id="@+id/bottom_bar" android:layout_width="match_parent" android:layout_height="51dp"> <ImageButton android:id="@+id/ib_home" android:src="@drawable/tab_home_selector" style="@style/BottomButtonTheme" /> <ImageButton android:id="@+id/ib_explore" android:src="@drawable/tab_explore_selector" style="@style/BottomButtonTheme" /> <ImageButton android:id="@+id/ib_notifications" android:src="@drawable/tab_notificaions_selector" style="@style/BottomButtonTheme" /> <ImageButton android:id="@+id/ib_profile" android:src="@drawable/tab_profile_selector" style="@style/BottomButtonTheme" /> </LinearLayout> </RelativeLayout>
Step 1:從xml中實例化頭尾bar
mBottom_bar = (LinearLayout) findViewById(R.id.bottom_bar); mHead_bar = (LinearLayout) findViewById(R.id.head_bar);
Step 2:實現listview的觸摸事件:
mlistView.setOnTouchListener(new View.OnTouchListener() { private float mEndY; private float mStartY; private int direction;//0表示向上,1表示向下 @Override public boolean onTouch(View v, MotionEvent event) { switch (event.getAction()){ case MotionEvent.ACTION_DOWN: mStartY = event.getY(); break; case MotionEvent.ACTION_MOVE: mEndY = event.getY(); float v1 = mEndY - mStartY; if (v1 > 3 && !isRunning&& direction == 1) { direction = 0; showBar(); mStartY = mEndY; return false; } else if (v1 < -3 && !isRunning && direction == 0) { direction = 1; hideBar(); mStartY = mEndY; return false; } mStartY = mEndY; break; case MotionEvent.ACTION_UP: break; } return false; } }); //隱藏頭尾bar的方法(這裏咱們用的是屬性動畫) public void hideBar() { mHeaderAnimator = ObjectAnimator.ofFloat(mHead_bar, "translationY", -mHead_bar.getHeight()); mBottomAnimator = ObjectAnimator.ofFloat(mBottom_bar, "translationY", mBottom_bar.getHeight()); mHeaderAnimator.setDuration(300).start(); mBottomAnimator.setDuration(300).start(); mHeaderAnimator.addListener(new AnimatorListenerAdapter() { @Override public void onAnimationStart(Animator animation) { super.onAnimationStart(animation); isRunning = true; } @Override public void onAnimationEnd(Animator animation) { super.onAnimationEnd(animation); isRunning = false; } }); } //顯示頭尾bar的方法 public void showBar() { mHeaderAnimator = ObjectAnimator.ofFloat(mHead_bar, "translationY", 0); mBottomAnimator = ObjectAnimator.ofFloat(mBottom_bar, "translationY", 0); mHeaderAnimator.setDuration(300).start(); mBottomAnimator.setDuration(300).start(); }
注:
這裏我再一次使用了標識符的手法,
第一個是經過改變isRunning的狀態來判斷動畫是結束!不然在快速滑動時,咱們動畫會有卡頓的現象!
第二個是經過direction標識符,來判斷滑動的方向,這樣也是爲了保證在向同一個方向上產生觸摸滑動時,不會由於每一小段距離的滑動就調用一次動畫從而致使動畫不暢!
你們若是想看一下這兩個標誌符是怎樣影響效果的,那麼可clone一下代碼而後本身把值替換掉試試看!
老規矩最後看一下咱們仿掘金的效果圖:
該項目的github地址:https://github.com/luorenyu/JuejinMoudel.git
若是你們以爲還不錯的能夠把github上面的代碼download下來看一下!若是是新手或初學者也能夠本身敲一下!這個Demo中基本含蓋了listview大多數經常使用內容的操做!另外這個Demo中還有別的一些東西是能夠分享的。好比帶波紋效果的button,好比關於SwipeRefreshLayout實現下拉刷新的使用等等!這些都會在接下來的時間一一和你們分享!另外,這個仿掘金app實現了這一個頁面,其餘的點擊事件什麼都尚未作!不過,我會持續更新它的!如今,我愈來愈以爲實操是學習和探索一項技能最好的方式,書寫是總結和梳理或者用咱們的術語是「抽象」咱們實操內容最好的方法!但願這兩句話也能幫助到你們!