可折叠/展开视图与滑动RecyclerView协调

11

我正在尝试实现以下效果(也请参见下面的图像):

  • 应用程序打开时,视图(地图)部分可见, RecyclerView 位于默认锚点(中心图像)
  • 用户向上滚动 RecyclerView ,地图会折叠,列表继续滚动(右图)
  • 用户向下滚动 RecyclerView ,地图会扩展到最大点(请注意,列表不应完全滑出屏幕,而是到达某个固定点)(左侧图像)

输入图像描述


请看下面我的回答。 - AndyRoid
2个回答

11

为了创建这个,我们需要 1 Activity 和 3 个 Fragment

Activity 将托管一个 TabLayout 和一个 ViewPager,就像这样:

<LinearLayout 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:orientation="vertical">

    <android.support.design.widget.TabLayout
        android:id="@+id/tabs"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
        app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" />

    <android.support.v4.view.ViewPager
        android:id="@+id/viewpager"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

</LinearLayout>

因为我们只需要对第一个Fragment进行滑动行为,所以第一个Fragment的XML布局如下:

<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.AppBarLayout
        android:id="@+id/appBarLayout"
        android:layout_width="match_parent"
        android:layout_height="400dp"
        android:orientation="vertical"
        android:fitsSystemWindows="true">

        <android.support.design.widget.CollapsingToolbarLayout
            android:id="@+id/collapsingToolbar"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:fitsSystemWindows="true"
            app:layout_scrollFlags="scroll|exitUntilCollapsed"
            app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">

            <com.google.android.gms.maps.MapView
                android:id="@+id/mapView"
                app:layout_collapseMode="parallax"
                android:layout_height="400dp"
                android:layout_width="match_parent" />

        </android.support.design.widget.CollapsingToolbarLayout>

    </android.support.design.widget.AppBarLayout>

    <FrameLayout
        android:id="@+id/content"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:layout_behavior="@string/appbar_scrolling_view_behavior"/>


</android.support.design.widget.CoordinatorLayout>
你可以按照自己的喜好创建其它的Fragment,我只是创建了假数据和一个简单的RecyclerView用于其他Fragment。然后在你的ActivityFragment中这样调用这些视图:

Activity

public class MainActivity extends AppCompatActivity {

    private TabLayout mTabLayout;
    private ViewPager mViewPager;
    private SampleViewPagerAdapter mViewPagerAdapter;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.another_activity);

        mTabLayout = (TabLayout) findViewById(R.id.sliding_tabs);
        mViewPager = (ViewPager) findViewById(R.id.viewpager);
        mViewPagerAdapter = new SampleViewPagerAdapter(getSupportFragmentManager());
        mViewPager.setAdapter(mViewPagerAdapter);
        mTabLayout.setupWithViewPager(mViewPager);
    }

}

ViewPager适配器

public class SampleViewPagerAdapter extends FragmentPagerAdapter {

    public SampleViewPagerAdapter(FragmentManager fm) {
        super(fm);
    }

    @Override
    public Fragment getItem(int position) {
        switch (position) {
            case 0:
                return new MapFragment();
            case 1:
                return new ScrollFragment();
            case 2:
                return new ScrollFragment();
            default:
                return new ScrollFragment();
        }
    }

    @Override
    public int getCount() {
        return 3;
    }

    @Override
    public CharSequence getPageTitle(int position) {
        String[] tabNames = {"Stops", "Planner", "Alerts"};
        return tabNames[position];
    }

}

带有滑动RecyclerView的地图片段

public class MapFragment extends Fragment {

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View root = inflater.inflate(R.layout.activity_main, null);

        initCollapsingToolbar(root);
        // Initialize map
        initFragment();
        return root;
    }

    private void initCollapsingToolbar(View root) {
        CollapsingToolbarLayout collapsingToolbarLayout =
            (CollapsingToolbarLayout) root.findViewById(R.id.collapsingToolbar);
        collapsingToolbarLayout.setContentScrimColor(getResources().getColor(R.color.cyan_500));
    }

    private void initFragment() {
        FakeDataFragment fragment = new FakeDataFragment();
        getChildFragmentManager().beginTransaction()
                .replace(R.id.content, scrollFragment)
                .commit();
    }

}

然后你应该会得到类似这样的东西:

设置位置:

您可以使用以下代码编程方式折叠工具栏 (CollapsingToolbarLayout) :

public void collapseToolbar(){
    CoordinatorLayout.LayoutParams params = (CoordinatorLayout.LayoutParams) mFrameLayout.getLayoutParams();
    AppBarLayout.ScrollingViewBehavior behavior = (AppBarLayout.ScrollingViewBehavior) params.getBehavior();
    if (behavior != null) {
        behavior.onNestedFling(rootLayout, appbarLayout, null, 0, 10000, true);
    }
}

这意味着当用户首次查看地图时,地图会部分折叠到您的默认状态。


谢谢Andy,除了一个例外,一切都很好。这个方法从地图完全展开开始(我的左边的图片),但是RecyclerView应该处于默认位置(我的中间的图片)。 - Ryan R
我已经彻底回答了你的问题,而你的评论超出了这个问题的范围。你的问题清楚地说明了“与滑动RecyclerView协调的折叠/展开视图”,并没有提到任何关于CollapsingToolbarLayoutAppBarLayout.Behavior的内容,这完全超出了范围,尽管如此,我仍然彻底回答了你的评论。你可以使用AppBarLayout.ScrollingViewBehavior来调整你的依赖视图的位置。 - AndyRoid
请问您能否友好地分享整个解决方案,@AndyRoid? - Alex Sorokoletov

0

我找到了CoordinatorLayout中标签页的解决方案

 <?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:id="@+id/htab_maincontent"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fitsSystemWindows="true">

        <android.support.design.widget.AppBarLayout
            android:id="@+id/htab_appbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:fitsSystemWindows="true"
            android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">

            <android.support.design.widget.CollapsingToolbarLayout
                android:id="@+id/htab_collapse_toolbar"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:fitsSystemWindows="true"
                app:layout_scrollFlags="scroll|enterAlways|snap"
                app:statusBarScrim="@null"
                app:titleEnabled="false">

                <LinearLayout
                    android:id="@+id/isprofile"
                    android:layout_width="match_parent"
                    android:layout_height="180dp"
                    android:background="@drawable/profile_cover"
                    android:gravity="center"
                    app:layout_collapseMode="parallax">

                    <LinearLayout
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:layout_gravity="center"
                        android:layout_marginBottom="10dp"
                        android:gravity="center"
                        android:orientation="vertical">


                        <com.root.findagame.utills.CircleImageView
                            android:id="@+id/profile_pic"
                            android:layout_width="60dp"
                            android:layout_height="60dp"
                            android:background="@drawable/profile_pic" />

                        <TextView
                            android:id="@+id/txtUserName"
                            android:layout_width="wrap_content"
                            android:layout_height="wrap_content"
                            android:text=""
                            android:textColor="@color/cpb_white"
                            android:textSize="@dimen/text_medium_size"
                            android:textStyle="bold" />

                        <TextView
                            android:id="@+id/txtAge"
                            android:layout_width="wrap_content"
                            android:layout_height="wrap_content"
                            android:layout_gravity="center"

                            android:text=""
                            android:textColor="@color/cpb_white"
                            android:textSize="@dimen/text_small_size" />


                        <TextView
                            android:id="@+id/txtName"
                            android:layout_width="wrap_content"
                            android:layout_height="wrap_content"
                            android:layout_gravity="center"
                            android:text=""
                            android:textColor="@color/cpb_white"
                            android:textSize="@dimen/text_small_size"
                            android:visibility="gone" />

                    </LinearLayout>
                </LinearLayout>

                <android.support.v7.widget.Toolbar
                    android:id="@+id/htab_toolbar"
                    android:layout_width="match_parent"
                    android:layout_height="40dp"
                    android:visibility="gone"
                    app:layout_collapseMode="pin"
                    app:layout_scrollFlags="scroll|exitUntilCollapsed|snap"
                    app:popupTheme="@style/AppTheme.PopupOverlay" />


            </android.support.design.widget.CollapsingToolbarLayout>
            <android.support.design.widget.TabLayout
                android:id="@+id/htab_tabs"
                android:layout_width="match_parent"
                android:layout_height="40dp"
                android:layout_gravity="bottom"
                android:background="@color/cpb_white"
                app:layout_collapseMode="pin"
                app:tabIndicatorColor="#7CC142"
                app:tabSelectedTextColor="#7CC142"
                app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
                app:tabTextAppearance="@android:style/TextAppearance.Widget.TabWidget"
                app:tabTextColor="@color/lightGrayColor" />

        </android.support.design.widget.AppBarLayout>


        <android.support.v4.view.ViewPager
            android:id="@+id/htab_viewpager"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            app:layout_behavior="@string/appbar_scrolling_view_behavior" />

    </android.support.design.widget.CoordinatorLayout>






*Fragment*
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/dummyfrag_bg"
    android:layout_width="match_parent"

    android:layout_height="match_parent">

    <android.support.v7.widget.RecyclerView
        android:id="@+id/dummyfrag_scrollableview"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:clipToPadding="false" />

</FrameLayout>

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接