Android 實現懸浮的幾種方式(一)AppBarLayout+PtrFrameLayout
阿新 • • 發佈:2019-01-07
先上個圖:
我所知道的有兩種實現方式:
AppBarLayout巢狀控制滾動區實現(目前使用的)
給RecyclerView增加HeaderView顯示隱藏切換實現
先把引用的包放出來:
compile 'com.android.support:cardview-v7:23.2.1'
compile 'com.jakewharton:butterknife:7.0.1'
compile 'com.zhy:base-rvadapter:3.0.3'
compile 'com.zhy:base-adapter:3.0.3'
compile 'cn.finalteam.loadingviewfinal:ultra-pull-to -refresh:1.0.1'
compile 'cn.finalteam.loadingviewfinal:loading-more-view:1.0.1'
先說第一種吧(不需要headerview,上方佈局,下方recycleView):
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout 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:id="@+id/stateView"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.design.widget.CoordinatorLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows ="true">
<android.support.design.widget.AppBarLayout
android:id="@+id/appbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:elevation="0dp">
<!--需要跟著RecyclerView一起滾動的,設定 app:layout_scrollFlags="scroll|enterAlways"-->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
app:layout_scrollFlags="scroll|enterAlways">
<include layout="@layout/layout_line" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_vertical"
android:padding="@dimen/d_15dp">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="您已篩選"
android:textColor="@color/gray_a"
android:textSize="13sp" />
<TextView
android:id="@+id/tv_time_result"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="3dp"
android:layout_marginRight="3dp"
android:text="今日"
android:textColor="@color/gray_64"
android:textSize="13sp" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="的生產裝箱情況"
android:textColor="@color/gray_a"
android:textSize="13sp" />
</LinearLayout>
<include layout="@layout/layout_line" />
</LinearLayout>
<!--放在layout的外面appbar的裡面就可以懸浮了 -->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@android:color/white"
android:orientation="vertical"
android:padding="@dimen/d_15dp">
<TextView
android:id="@+id/tv_product_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/common_null"
android:textColor="@color/gray_32"
android:textSize="13sp" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:paddingTop="29dp">
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:gravity="center"
android:orientation="vertical">
<TextView
android:id="@+id/tv_product_boxs"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/common_null"
android:textColor="@color/gray_32"
android:textSize="28dp" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/d_10dp"
android:text="箱"
android:textColor="@color/gray_a"
android:textSize="13sp" />
</LinearLayout>
<TextView
android:layout_width="1dp"
android:layout_height="match_parent"
android:background="@color/lineColor" />
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:gravity="center"
android:orientation="vertical">
<TextView
android:id="@+id/tv_product_singles"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/common_null"
android:textColor="@color/gray_32"
android:textSize="28dp" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/d_10dp"
android:text="單標"
android:textColor="@color/gray_a"
android:textSize="13sp" />
</LinearLayout>
</LinearLayout>
</LinearLayout>
<include layout="@layout/layout_line" />
</android.support.design.widget.AppBarLayout>
<cn.finalteam.loadingviewfinal.PtrClassicFrameLayout
app:layout_behavior="@string/appbar_scrolling_view_behavior"
android:id="@+id/ptr_rv_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:ptr_duration_to_close="300"
app:ptr_duration_to_close_header="1500"
app:ptr_keep_header_when_refresh="true"
app:ptr_ratio_of_header_height_to_refresh="1.2"
app:ptr_resistance="1.7">
<cn.finalteam.loadingviewfinal.RecyclerViewFinal
android:id="@+id/rv_list"
android:layout_width="match_parent"
android:layout_height="match_parent"
/>
</cn.finalteam.loadingviewfinal.PtrClassicFrameLayout>
</android.support.design.widget.CoordinatorLayout>
</FrameLayout>
總結:
對於需要跟著RecyclerView一起滾動消失的父佈局,設定
app:layout_scrollFlags="scroll|enterAlways;
希望懸浮的,放在(滾動佈局)LinearLayout的外面AppBarLayout的裡面就可以懸浮了。
AppBarLayout裡面只存在2種佈局:滾動的和懸浮的
- 對於滾動的主佈局裡面新增
app:layout_behavior="@string/appbar_scrolling_view_behavior"
這樣結束了,activity裡面正常載入RecyclerView就可以了
mRvList.setLayoutManager(new LinearLayoutManager(this));
mCommonAdapter = new CommonAdapter();
mRvList.setAdapter(mCommonAdapter);
這就簡單實現了懸浮的功能了。
但是我這裡加入了下拉重新整理的功能,出現了下拉重新整理先於AppbarLayout的問題,即下拉的時候,頁面還沒完全拉下來就觸發了重新整理功能
我這裡的解決:
第一步:實現OnOffsetChangedListener並重寫onOffsetChanged
public class BoxingProductChartActivity extends StateViewActivity implements AppBarLayout.OnOffsetChangedListener
第二步:當verticalOffset == 0,設定允許重新整理
@Override
public void onOffsetChanged(AppBarLayout appBarLayout, int verticalOffset) {
if (verticalOffset == 0) {
setCanRefresh(true);
} else {
setCanRefresh(false);
}
}
private boolean canRefresh;
public void setCanRefresh(boolean canRefresh) {
this.canRefresh = canRefresh;
}
第三步:設定給PtrClassicFrameLayout(下拉重新整理)
@Bind(R.id.ptr_rv_layout)
PtrClassicFrameLayout mPtrRvLayout;
mPtrRvLayout.setOnRefreshListener(new OnDefaultRefreshListener() {
@Override
public boolean checkCanDoRefresh(PtrFrameLayout frame, View content, View header) {
return canRefresh && OnDefaultRefreshListener.checkContentCanBePulledDown(frame, content, header);
}
@Override
public void onRefreshBegin(PtrFrameLayout frame) {
requestData();
}
});
大功告成!就是圖中現在的情況了
附加:由於上方程式碼用到一些第三方庫,下面貼一個簡潔的。使用這種方式只要佈局調整好了就好了,不需要寫任何java程式碼的。。
<?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:fitsSystemWindows="true"-->
<android.support.design.widget.AppBarLayout
android:id="@+id/appbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:fitsSystemWindows="true">
<!--注意點二:需要跟著RecyclerView一起滾動的,設定 app:layout_scrollFlags="scroll|enterAlways"-->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
app:layout_scrollFlags="scroll|enterAlways">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="20dp"
android:text="我是被滑動出去的view"
android:textColor="@color/gray_a"
android:textSize="13sp" />
</LinearLayout>
<!--注意點三:放在layout的外面appbar的裡面就可以懸浮了 -->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@android:color/white"
android:orientation="vertical"
android:padding="15dp">
<TextView
android:id="@+id/tv_product_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="我是懸浮-標題欄"
android:textColor="@color/gray_32"
android:textSize="13sp" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:text="我是懸浮-內容"
android:textColor="@color/gray_a"
android:textSize="13sp" />
</LinearLayout>
<include layout="@layout/layout_line" />
</android.support.design.widget.AppBarLayout>
<!-- 注意點四:app:layout_behavior="@string/appbar_scrolling_view_behavior" -->
<android.support.v7.widget.RecyclerView
android:id="@+id/rv_list"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior" />
</android.support.design.widget.CoordinatorLayout>