參考:
MD基礎控件簡書:https://www.jianshu.com/p/e2ae6aaff696
Behavior簡書:https://www.jianshu.com/p/82d18b0d18f4
MD常用控件詳解
Material Design中的一些常見控件的使用
ToolBar
Toolbar 是應用內的action bars的一個歸納。
Toolbar使用來替代原來的ActionBar的就行了。
Toolbar是一個ViewGroup容器!
- Navigation Button
- Logo Image
- title
- subtitle
- 一個或多個自定義的View
- Action Menu
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<android.support.v7.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="55dp"
android:background="@color/colorPrimaryDark"
android:gravity="center"
app:navigationIcon="@mipmap/more"
app:subtitle="下一步"
app:subtitleTextColor="@android:color/white"
app:title="首頁"
app:titleTextColor="@android:color/white" />
</android.support.design.widget.CoordinatorLayout>
private void initView() {
toolbar = findViewById(R.id.toolbar);
toolbar.inflateMenu(R.menu.layout_toolbar_menu);
//點擊溢出菜單的點擊事件
toolbar.setOnMenuItemClickListener(new Toolbar.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem menuItem) {
return false;
}
});
//點擊導航按鈕的點擊事件
//toolbar.setNavigationOnClickListener();
}
AppbarLayout
AppbarLayout繼承自LinearLayout,它就是一個垂直方向的LinearLayout,在LinearLayout的基礎上添加了一些材料設計的概念和特性,即滑動手勢。
它可以讓你定製在某個可滑動的View(如:ScrollView ,ListView ,RecyclerView 等)滑動手勢發生改變時,內部的子View 該做什麼動作。子View應該提供滑動時他們期望的響應的動作Behavior,通過setScrollFlags(int),或者xml中給需要滑動的子控件使用屬性app:layout_scrollFlags=“”。layout_scrollFlags屬性中的幾個屬性(對應的是AppbarLayout中Behavior的一些邏輯處理)
AppbarLayout中的layout_scrollFlags幾個參數:
-
scroll
子View添加layout_scrollFlags屬性的值scroll時,這個View將會隨着可滾動View(如:ScrollView)一起滾動,就好像子View是屬於ScrollView的一部分一樣。 -
enterAlways
子View添加layout_scrollFlags屬性的值有enterAlways時, 當滑動控件向下滑動時,子View將直接向下滑動,而不管滑動控件是否在滑動。注意:要與滑動控件搭配使用,否者是不能滑動的。 -
enterAlwaysCollapsed
enterAlwaysCollapsed是對enterAlways的補充,當滑動控件向下滑動的時候,滑動View(也就是設置了enterAlwaysCollapsed 的View)下滑至摺疊的高度,當滑動控件到達滑動範圍的結束值的時候,滑動View剩下的部分開始滑動。這個摺疊的高度是通過View的minimum height (最小高度)指定的。 -
exitUntilCollapsed
當滑動控件滑出屏幕時(也就是向上滑動時),滑動View先響應滑動事件,滑動至摺疊高度,也就是通過
minimum height 設置的最小高度後,就固定不動了,再把滑動事件交給 scrollview 繼續滑動。 -
snap
在滾動結束後,如果view只是部分可見,它將滑動到最近的邊界。比如,如果view的底部只有25%可見,它將
滾動離開屏幕,而如果底部有75%可見,它將滾動到完全顯示。
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.design.widget.AppBarLayout
android:id="@+id/appbar_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:background="@color/colorAccent"
android:gravity="bottom"
android:minHeight="50dp"
android:text="首頁"
app:layout_scrollFlags="scroll|snap" />
</android.support.design.widget.AppBarLayout>
<android.support.v4.widget.NestedScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="111" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="222" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="333" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="444" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="555" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="666" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="777" />
</LinearLayout>
</android.support.v4.widget.NestedScrollView>
</android.support.design.widget.CoordinatorLayout>
TabLayout
TabLayout是Tab控件的容器,封裝了多個操作Tab控件的屬性,
能讓不同視圖和功能之間的切換變得簡單。
Tab的大多屬性是在TabLayout中進行設值:
- app:tabIndicatorColor 設置指示器的顏色(默認情況下指示器的顏色爲colorAccent)
- app:tabIndicatorHeight 設置指示器的高度,Material Design 規範建議是2dp
- app:tabMaxWidth 設置 Tab 的最大寬度
- app:tabMinWidth 設置 Tab 的最小寬度
- app:tabMode 設置Tabs的顯示模式,有兩個常量值,MODE_FIXED,MODE_SCROLLABLE。用法:app:tabMode="fixed"或者app:tabMode=“scrollable”
- app:tabSelectedTextColor 設置Tab選中後,文字顯示的顏色
- app:tabTextColor 設置Tab未選中,文字顯示的顏色
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.design.widget.TabLayout
android:id="@+id/tabLayout"
android:layout_width="match_parent"
android:layout_height="50dp"
android:background="@color/white"
app:tabGravity="center"
app:tabIndicatorColor="@color/colorAccent"
app:tabIndicatorHeight="2dp"
app:tabMode="fixed"
app:tabSelectedTextColor="@color/colorAccent"
app:tabTextColor="@android:color/black">
<android.support.design.widget.TabItem
android:layout_width="match_parent"
android:layout_height="match_parent"
android:text="默認" />
<android.support.design.widget.TabItem
android:layout_width="match_parent"
android:layout_height="match_parent"
android:text="銷量" />
<android.support.design.widget.TabItem
android:layout_width="match_parent"
android:layout_height="match_parent"
android:text="價格" />
</android.support.design.widget.TabLayout>
</android.support.design.widget.CoordinatorLayout>
private void initView() {
tabLayout = findViewById(R.id.tabLayout);
//動態設置tabs
tabLayout.addTab(tabLayout.newTab().setText("綜合"));
tabLayout.addTab(tabLayout.newTab().setText("銷量"));
tabLayout.addTab(tabLayout.newTab().setText("價格"));
tabLayout.addOnTabSelectedListener(new TabLayout.BaseOnTabSelectedListener() {
@Override
public void onTabSelected(TabLayout.Tab tab) {
//被選中 這個地方有個坑 點擊第一個 不會有變化 因爲第一個以及是選中狀態
Log.e("DN_TAB_0----->",tab.getText().toString()+"");
}
@Override
public void onTabUnselected(TabLayout.Tab tab) {
//被取消
Log.e("DN_TAB_1----->",tab.getText().toString()+"");
}
@Override
public void onTabReselected(TabLayout.Tab tab) {
//重複選中
Log.e("DN_TAB_3----->",tab.getText().toString()+"");
}
});
}
CollapsingToolbarLayout
CollapsingToolbarLayout是一個摺疊的Toolbar,它能夠設置一種顏色或者一張圖片來遮擋它裏面的內容。
推薦CoordinatorLayout + AppBarLayout + CollapsingToolbarLayout一起使用
- Collapsing title–>摺疊標題
- Content scrim–>內容紗布
- Status bar scrim–>狀態欄紗布
- Parallax scrolling children–>有視差地滾動子View
- Pinned position children–>固定子View的位置
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.design.widget.AppBarLayout
android:id="@+id/appbar_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<android.support.design.widget.CollapsingToolbarLayout
android:id="@+id/collapse_layout"
android:layout_width="match_parent"
android:layout_height="250dp"
app:layout_scrollFlags="scroll|exitUntilCollapsed">
<ImageView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scaleType="centerCrop"
android:src="@mipmap/timg"
app:layout_collapseMode="parallax" />
<android.support.v7.widget.Toolbar
android:id="@+id/appbar_layout_toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
app:layout_collapseMode="pin"
app:navigationIcon="@mipmap/more"
app:title="AppbarLayout"
app:titleTextColor="@android:color/white" />
</android.support.design.widget.CollapsingToolbarLayout>
</android.support.design.widget.AppBarLayout>
<android.support.v4.widget.NestedScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="111" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="222" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="333" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="444" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="555" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="666" />
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="777" />
</LinearLayout>
</android.support.v4.widget.NestedScrollView>
</android.support.design.widget.CoordinatorLayout>
private void initView() {
final Toolbar toolbar = findViewById(R.id.appbar_layout_toolbar);
//設置沉浸式狀態欄
StatusBarUtils.setTranslucentImageHeader(this, 0, toolbar);
//設置標題顏色
toolbar.setTitleTextColor(Color.TRANSPARENT);
//加載動作菜單
toolbar.inflateMenu(R.menu.layout_toolbar_menu);
AppBarLayout appBarLayout = findViewById(R.id.appbar_layout);
final CollapsingToolbarLayout collapsingToolbarLayout = findViewById(R.id.collapse_layout);
collapsingToolbarLayout.setTitle("");
collapsingToolbarLayout.setCollapsedTitleTextColor(getResources().getColor(R.color.white));
collapsingToolbarLayout.setExpandedTitleColor(getResources().getColor(R.color.white));
collapsingToolbarLayout.setExpandedTitleColor(Color.TRANSPARENT);
//設置紗布
collapsingToolbarLayout.setContentScrimColor((getResources().getColor(R.color.colorAccent)));
//監聽appBarLayout的偏移
appBarLayout.addOnOffsetChangedListener(new AppBarLayout.OnOffsetChangedListener() {
@Override
public void onOffsetChanged(AppBarLayout appBarLayout, int verticalOffset) {
if (Math.abs(verticalOffset) >= appBarLayout.getTotalScrollRange()) {
toolbar.setTitleTextColor(getResources().getColor(R.color.white));
collapsingToolbarLayout.setTitle("AppbarLayout");
} else {
collapsingToolbarLayout.setTitle("");
}
}
});
}
CardView
CardView就是一個幀佈局,但是它裏面封裝了很多屬性,
包括圓角,陰影等。
- app:cardBackgroundColor–>卡片顏色
- app:cardCornerRadius–>卡片圓角
- app:cardElevation–>卡片陰影
- app:cardUseCompatPadding–>padding
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<android.support.v7.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="10dp"
android:layout_marginBottom="0dp"
android:clickable="true"
android:foreground="?attr/selectableItemBackground"
app:cardCornerRadius="10dp"
app:cardElevation="3dp">
<ImageView
android:layout_width="match_parent"
android:layout_height="150dp"
android:scaleType="center"
android:src="@mipmap/meizhi" />
</android.support.v7.widget.CardView>
</LinearLayout>
<android.support.design.widget.BottomNavigationView
android:layout_width="match_parent"
android:layout_height="50dp"
android:layout_gravity="bottom"
app:menu="@menu/layout_toolbar_menu">
</android.support.design.widget.BottomNavigationView>
</android.support.design.widget.CoordinatorLayout>
Behavior中的方法詳解
Behavior中的一些方法詳解
import android.content.Context;
import android.support.annotation.NonNull;
import android.support.design.widget.CoordinatorLayout;
import android.support.v4.widget.NestedScrollView;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
/**
* BeHavior常用的方法詳解
*/
public class MyBeHavior extends CoordinatorLayout.Behavior {
//列表頂部和textView之間的距離
private float deltaY;
public MyBeHavior(Context context, AttributeSet attributeSet) {
super(context, attributeSet);
}
/**
* 表示是否給應用了Behavior 的View 指定一個觀察的佈局,通常,當觀察的View 佈局發生變化時
* 不管被觀察View 的順序怎樣,被觀察的View也會重新佈局
*
* @param parent
* @param child 綁定behavior 的View 觀察者
* @param dependency 被觀察者的view
* @return 如果child 是觀察者觀察的View 返回true,否則返回false
*/
@Override
public boolean layoutDependsOn(CoordinatorLayout parent, View child, View dependency) {
return dependency instanceof NestedScrollView;
}
/**
* 當被觀察者的View 狀態(如:位置、大小)發生變化時,這個方法被調用
*
* @param parent
* @param child
* @param dependency
* @return
*/
@Override
public boolean onDependentViewChanged(CoordinatorLayout parent, View child, View dependency) {
if (deltaY == 0) {
deltaY = dependency.getY() - child.getHeight();
}
//被觀察者View的Y座標 - 觀察者的高度 得到的就是兩者之間的距離
float dy = dependency.getY() - child.getHeight();
//如果兩者之間的距離小於0 就賦值爲0 如果兩者之間的距離不小於0 就將兩者之間的實際距離賦值給它
dy = dy < 0 ? 0 : dy;
//計算Y軸每次偏移的距離
float y = -(dy / deltaY) * child.getHeight();
Log.e("BEHAVIOR----->", y + "-------------");
//將編譯距離設置給觀察者
child.setTranslationY(y);
return false;
}
/**
* 當coordinatorLayout 的子View試圖開始嵌套滑動的時候被調用。當返回值爲true的時候表明
* coordinatorLayout 充當nested scroll parent 處理這次滑動,需要注意的是隻有當返回值爲true
* 的時候,Behavior 才能收到後面的一些nested scroll 事件回調(如:onNestedPreScroll、onNestedScroll等)
* 這個方法有個重要的參數nestedScrollAxes,表明處理的滑動的方向。
*
* @param coordinatorLayout 和Behavior 綁定的View的父CoordinatorLayout
* @param child 和Behavior 綁定的View 觀察者
* @param directTargetChild
* @param target
* @param nestedScrollAxes 嵌套滑動 應用的滑動方向
* @param type
* @return
*/
@Override
public boolean onStartNestedScroll(CoordinatorLayout coordinatorLayout, View child, View directTargetChild,
View target, int nestedScrollAxes, int type) {
child.setVisibility(View.GONE);
return false;
}
/**
* 嵌套滾動發生之前被調用
* 在nested scroll child 消費掉自己的滾動距離之前,嵌套滾動每次被nested scroll child
* 更新都會調用onNestedPreScroll。注意有個重要的參數consumed,可以修改這個數組表示你消費
* 了多少距離。假設用戶滑動了100px,child 做了90px 的位移,你需要把 consumed[1]的值改成90,
* 這樣coordinatorLayout就能知道只處理剩下的10px的滾動。
*
* @param coordinatorLayout
* @param child
* @param target
* @param dx 用戶水平方向的滾動距離
* @param dy 用戶豎直方向的滾動距離
* @param consumed
*/
@Override
public void onNestedPreScroll(CoordinatorLayout coordinatorLayout, View child, View target, int dx, int dy, int[] consumed, int type) {
super.onNestedPreScroll(coordinatorLayout, child, target, dx, dy, consumed, type);
}
/**
* 進行嵌套滾動時被調用
*
* @param coordinatorLayout
* @param child
* @param target
* @param dxConsumed target 已經消費的x方向的距離
* @param dyConsumed target 已經消費的y方向的距離
* @param dxUnconsumed x 方向剩下的滾動距離
* @param dyUnconsumed y 方向剩下的滾動距離
*/
@Override
public void onNestedScroll(CoordinatorLayout coordinatorLayout, View child, View target, int dxConsumed,
int dyConsumed, int dxUnconsumed, int dyUnconsumed, int type) {
super.onNestedScroll(coordinatorLayout, child, target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, type);
}
/**
* 嵌套滾動結束時被調用,這是一個清除滾動狀態等的好時機。
*
* @param coordinatorLayout
* @param child
* @param target
*/
@Override
public void onStopNestedScroll(CoordinatorLayout coordinatorLayout, View child, View target, int type) {
super.onStopNestedScroll(coordinatorLayout, child, target, type);
}
/**
* onStartNestedScroll返回true纔會觸發這個方法,接受滾動處理後回調,可以在這個
* 方法裏做一些準備工作,如一些狀態的重置等。
*
* @param coordinatorLayout
* @param child
* @param directTargetChild
* @param target
* @param nestedScrollAxes
*/
@Override
public void onNestedScrollAccepted(CoordinatorLayout coordinatorLayout, View child, View directTargetChild,
View target, int nestedScrollAxes, int type) {
super.onNestedScrollAccepted(coordinatorLayout, child, directTargetChild, target, nestedScrollAxes, type);
}
/**
* 用戶鬆開手指並且會發生慣性動作之前調用,參數提供了速度信息,可以根據這些速度信息
* 決定最終狀態,比如滾動Header,是讓Header處於展開狀態還是摺疊狀態。返回true 表
* 示消費了fling.
*
* @param coordinatorLayout
* @param child
* @param target
* @param velocityX x 方向的速度
* @param velocityY y 方向的速度
* @return
*/
@Override
public boolean onNestedPreFling(CoordinatorLayout coordinatorLayout, View child, View target,
float velocityX, float velocityY) {
return super.onNestedPreFling(coordinatorLayout, child, target, velocityX, velocityY);
}
//可以重寫這個方法對子View 進行重新佈局
@Override
public boolean onLayoutChild(CoordinatorLayout parent, View child, int layoutDirection) {
return super.onLayoutChild(parent, child, layoutDirection);
}
/**
* 是否攔截觸摸
*
* @param parent
* @param child
* @param ev
* @return
*/
@Override
public boolean onInterceptTouchEvent(@NonNull CoordinatorLayout parent, @NonNull View child, @NonNull MotionEvent ev) {
return super.onInterceptTouchEvent(parent, child, ev);
}
}
自定義Behavior示例
public class BehaviorTest extends CoordinatorLayout.Behavior {
// 列表頂部和滾動控件的距離
private float deltaY;
public BehaviorTest(Context context, AttributeSet attributeSet){
super(context,attributeSet);
}
/**
* 表示是否給應用了Behavior 的View 指定一個觀察的佈局,通常,當觀察的View 佈局發生變化時
* 不管被觀察View 的順序怎樣,被觀察的View也會重新佈局
* @param parent
* @param child 綁定behavior 的View 觀察者
* @param dependency 被觀察者的view
* @return 如果child 是觀察者觀察的View 返回true,否則返回false
*/
@Override
public boolean layoutDependsOn(CoordinatorLayout parent, View child, View dependency) {
if(dependency instanceof NestedScrollView || dependency instanceof Button){
return true;
}
return false;
}
/**
* 當被觀察者的View 狀態(如:位置、大小)發生變化時,這個方法被調用
* @param parent
* @param child
* @param dependency
* @return
*/
@Override
public boolean onDependentViewChanged(CoordinatorLayout parent, View child, View dependency) {
//一開始 等於0
if (deltaY == 0) {
//初始化兩者之間的距離
deltaY = dependency.getY() - child.getHeight();
}
Log.e("DN deltaY------------>",deltaY+"------------");
//被觀察者View的Y座標 - 觀察者的高度 得到兩者之間剩餘的距離
float dy = dependency.getY() - child.getHeight();
//如果距離小於0 就賦值0 如果距離大於等於0 就把剩餘距離賦值給它
dy = dy < 0 ? 0 : dy;
//計算Y軸每次偏移的距離
float y = -(dy / deltaY) * child.getHeight();
Log.e("DN-------------->",y+"------------");
//設置Y軸的偏移參數
child.setTranslationY(y);
return true;
}
/**
* 當coordinatorLayout 的子View試圖開始嵌套滑動的時候被調用。當返回值爲true的時候表明
* coordinatorLayout 充當nested scroll parent 處理這次滑動,需要注意的是隻有當返回值爲true
* 的時候,Behavior 才能收到後面的一些nested scroll 事件回調(如:onNestedPreScroll、onNestedScroll等)
* 這個方法有個重要的參數nestedScrollAxes,表明處理的滑動的方向。
*
* @param coordinatorLayout 和Behavior 綁定的View的父CoordinatorLayout
* @param child 和Behavior 綁定的View 觀察者
* @param directTargetChild
* @param target
* @param nestedScrollAxes 嵌套滑動 應用的滑動方向
* @param type
*
* @return
*/
@Override
public boolean onStartNestedScroll(CoordinatorLayout coordinatorLayout, View child, View directTargetChild,
View target, int nestedScrollAxes, int type) {
return super.onStartNestedScroll(coordinatorLayout, child, directTargetChild, target, nestedScrollAxes,type);
}
/**
* 嵌套滾動發生之前被調用
* 在nested scroll child 消費掉自己的滾動距離之前,嵌套滾動每次被nested scroll child
* 更新都會調用onNestedPreScroll。注意有個重要的參數consumed,可以修改這個數組表示你消費
* 了多少距離。假設用戶滑動了100px,child 做了90px 的位移,你需要把 consumed[1]的值改成90,
* 這樣coordinatorLayout就能知道只處理剩下的10px的滾動。
* @param coordinatorLayout
* @param child
* @param target
* @param dx 用戶水平方向的滾動距離
* @param dy 用戶豎直方向的滾動距離
* @param consumed
*/
@Override
public void onNestedPreScroll(CoordinatorLayout coordinatorLayout, View child, View target, int dx, int dy, int[] consumed, int type) {
super.onNestedPreScroll(coordinatorLayout, child, target, dx, dy, consumed,type);
}
/**
* 進行嵌套滾動時被調用
* @param coordinatorLayout
* @param child
* @param target
* @param dxConsumed target 已經消費的x方向的距離
* @param dyConsumed target 已經消費的y方向的距離
* @param dxUnconsumed x 方向剩下的滾動距離
* @param dyUnconsumed y 方向剩下的滾動距離
*/
@Override
public void onNestedScroll(CoordinatorLayout coordinatorLayout, View child, View target, int dxConsumed,
int dyConsumed, int dxUnconsumed, int dyUnconsumed, int type) {
super.onNestedScroll(coordinatorLayout, child, target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed,type);
}
/**
* 嵌套滾動結束時被調用,這是一個清除滾動狀態等的好時機。
* @param coordinatorLayout
* @param child
* @param target
*/
@Override
public void onStopNestedScroll(CoordinatorLayout coordinatorLayout, View child, View target, int type) {
super.onStopNestedScroll(coordinatorLayout, child, target,type);
}
/**
* onStartNestedScroll返回true纔會觸發這個方法,接受滾動處理後回調,可以在這個
* 方法裏做一些準備工作,如一些狀態的重置等。
* @param coordinatorLayout
* @param child
* @param directTargetChild
* @param target
* @param nestedScrollAxes
*/
@Override
public void onNestedScrollAccepted(CoordinatorLayout coordinatorLayout, View child, View directTargetChild,
View target, int nestedScrollAxes,int type) {
super.onNestedScrollAccepted(coordinatorLayout, child, directTargetChild, target, nestedScrollAxes,type);
}
/**
* 用戶鬆開手指並且會發生慣性動作之前調用,參數提供了速度信息,可以根據這些速度信息
* 決定最終狀態,比如滾動Header,是讓Header處於展開狀態還是摺疊狀態。返回true 表
* 示消費了fling.
*
* @param coordinatorLayout
* @param child
* @param target
* @param velocityX x 方向的速度
* @param velocityY y 方向的速度
* @return
*/
@Override
public boolean onNestedPreFling(CoordinatorLayout coordinatorLayout, View child, View target,
float velocityX, float velocityY) {
return super.onNestedPreFling(coordinatorLayout, child, target, velocityX, velocityY);
}
//可以重寫這個方法對子View 進行重新佈局
@Override
public boolean onLayoutChild(CoordinatorLayout parent, View child, int layoutDirection) {
return super.onLayoutChild(parent, child, layoutDirection);
}
}
<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".view.BehaviorActivity">
<android.support.design.widget.AppBarLayout
android:id="@+id/app_bar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:elevation="0dp">
<android.support.design.widget.CollapsingToolbarLayout
android:id="@+id/toolbar_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:contentScrim="#00ffffff"
app:layout_scrollFlags="scroll|exitUntilCollapsed">
<ImageView
android:layout_width="match_parent"
android:layout_height="200dp"
android:background="@mipmap/meizhi"
android:fitsSystemWindows="true"
android:scaleType="fitXY"
app:layout_collapseMode="parallax"
app:layout_collapseParallaxMultiplier="0.7" />
</android.support.design.widget.CollapsingToolbarLayout>
</android.support.design.widget.AppBarLayout>
<android.support.v4.widget.NestedScrollView
android:id="@+id/scollView"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="111"/>
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="222"/>
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="333"/>
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="444"/>
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="555"/>
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="666"/>
<TextView
android:layout_width="match_parent"
android:layout_height="200dp"
android:text="777"/>
</LinearLayout>
</android.support.v4.widget.NestedScrollView>
<TextView
android:id="@+id/title"
android:layout_width="match_parent"
android:layout_height="50dp"
android:background="#ff0000"
android:gravity="center"
android:text="Hello World"
android:textColor="#ffffff"
android:textSize="18sp"
app:layout_behavior=".behavior.BehaviorTest"/>
</android.support.design.widget.CoordinatorLayout>