Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using a coordinatorlayout to collapse a full screen imageview and replace it with viewpager with headers

I started playing around with coordinatoralyout and I'm trying to achieve the behavior on the attached image, I want a background image to be on full screen size and upon a scroll I want some textviews to dissapear and some to stick as parts of a viewpager (rather then a toolbarlayout) any guidance on how can I achieve this?

enter image description here

like image 748
crazyPixel Avatar asked Apr 16 '16 00:04

crazyPixel


People also ask

What is the use of CoordinatorLayout?

CoordinatorLayout is a super-powered FrameLayout . CoordinatorLayout is intended for two primary use cases: As a top-level application decor or chrome layout. As a container for a specific interaction with one or more child views.

What is CoordinatorLayout and ConstraintLayout?

Use Coordinatorlayout as the top-level application decor. It will usually used to layout AppBarLayout , FloatingActionButton , and the main body of your screen, say NestedScrollView . Inside the NestedScrollView use ConstraintLayout to describe the rest of the layout as a flat hierarchy.

What is layout_collapseMode?

In addition to pinning a view, you can use app:layout_collapseMode="parallax" (and optionally app:layout_collapseParallaxMultiplier="0.7" to set the parallax multiplier) to implement parallax scrolling (say of a sibling ImageView within the CollapsingToolbarLayout ).


2 Answers

You can use layout_behavior to handle the strings which you want to be disappear upon scroll. Customise your view behaviour using CoordinatorLayout.Behavior

ViewBehavior.java

public class ViewBehavior extends CoordinatorLayout.Behavior<RelativeLayout> {

private Context mContext;

public ViewBehavior(Context context, AttributeSet attrs) {
    mContext = context;
}

@Override
public boolean layoutDependsOn(CoordinatorLayout parent, RelativeLayout child, View dependency) {
    return dependency instanceof AppBarLayout;
}

@Override
public boolean onDependentViewChanged(CoordinatorLayout parent, RelativeLayout child, View dependency) {
    child.measure(View.MeasureSpec.makeMeasureSpec(parent.getWidth(), View.MeasureSpec.EXACTLY), View.MeasureSpec.makeMeasureSpec(parent.getHeight(), View.MeasureSpec.AT_MOST));
    int maxScroll = ((AppBarLayout) dependency).getTotalScrollRange();
    float percentage = Math.abs(dependency.getY()) / (float) maxScroll;
    float childPosition = dependency.getHeight()
            + dependency.getY()
            - child.getMeasuredHeight()
            - (getToolbarHeight() - child.getMeasuredHeight()) * percentage / 2;

    CoordinatorLayout.LayoutParams lp = (CoordinatorLayout.LayoutParams) child.getLayoutParams();
    child.setLayoutParams(lp);

    child.setY(childPosition);
    return true;
}

public int getToolbarHeight() {
    int result = 0;
    TypedValue tv = new TypedValue();
    if (mContext.getTheme().resolveAttribute(android.R.attr.actionBarSize, tv, true)) {
        result = TypedValue.complexToDimensionPixelSize(tv.data, mContext.getResources().getDisplayMetrics());
    }
    return result;
}
}

In layout xml, set your custom view behaviour as a app:layout_behavior in the view you want to handle.

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

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

    <android.support.design.widget.CollapsingToolbarLayout
        android:id="@+id/collapsing_toolbar"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fitsSystemWindows="true"
        app:contentScrim="?attr/colorPrimary"
        app:layout_scrollFlags="scroll|exitUntilCollapsed">

        <ImageView
            android:id="@+id/image"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:fitsSystemWindows="true"
            app:layout_collapseMode="parallax" />

    </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"
    android:fillViewport="true"
    app:layout_behavior="@string/appbar_scrolling_view_behavior">

    <LinearLayout
        android:id="@+id/llViewPager"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical">

        <com.astuetz.PagerSlidingTabStrip
            android:id="@+id/tabs"
            android:layout_width="match_parent"
            android:layout_height="48dp"
            android:textColor="@color/red"
            app:pstsShouldExpand="true"
            app:pstsTextAllCaps="true" />

        <android.support.v4.view.ViewPager
            android:id="@+id/viewpager"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="@android:color/white" />
    </LinearLayout>
</android.support.v4.widget.NestedScrollView>

<RelativeLayout
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layout_behavior="com.stacktest.ViewBehavior">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_marginBottom="20dp"
        android:layout_marginLeft="36dp"
        android:layout_marginTop="20dp"
        android:text="Text-1" />

    <TextView
        android:id="@+id/txt2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentRight="true"
        android:layout_marginBottom="20dp"
        android:layout_marginRight="36dp"
        android:layout_marginTop="20dp"
        android:text="Text-2" />

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_below="@id/txt2"
        android:layout_marginBottom="20dp"
        android:layout_marginLeft="36dp"
        android:paddingRight="20dp"
        android:text="Text-3" />

    <TextView
        android:id="@+id/txt4"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentRight="true"
        android:layout_below="@id/txt2"
        android:layout_marginBottom="20dp"
        android:layout_marginRight="36dp"
        android:text="Text-4" />
</RelativeLayout>
</android.support.design.widget.CoordinatorLayout>

Finally, use the layout and create ViewPager and Tabs in your Activity class.

MainActivity.java

public class MainActivity extends AppCompatActivity {

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

    ((CollapsingToolbarLayout) findViewById(R.id.collapsing_toolbar)).setTitle(" ");

    ViewPager viewPager = (ViewPager) findViewById(R.id.viewpager);
    viewPager.setAdapter(new MyPagerAdapter(getSupportFragmentManager()));

    PagerSlidingTabStrip tabsStrip = (PagerSlidingTabStrip) findViewById(R.id.tabs);
    tabsStrip.setViewPager(viewPager);
}

public class MyPagerAdapter extends FragmentPagerAdapter {
    final int PAGE_COUNT = 2;
    private String tabTitles[] = new String[] { "Tab1", "Tab2" };

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

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

    @Override
    public Fragment getItem(int position) {
        return TestFragment.newInstance(position + 1);
    }

    @Override
    public CharSequence getPageTitle(int position) {
        return tabTitles[position];
    }
}
}

Add following extra dependency in build.gradle along with appcompat and support library.

  • com.android.support:design:23.2.1
  • com.astuetz:pagerslidingtabstrip:1.0.1 (for ViewPager tabs)
like image 121
Janak Rajyaguru Avatar answered Sep 28 '22 03:09

Janak Rajyaguru


As I am not sure if you want a particular or a general solution, I am going to give you my solution for your particular question. The key is to work with scrollFlags and collapseMode. If you really want to hide the tabs when the appBar is expanded, you can play with visibility.

<?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/main_content"
android:layout_width="match_parent"
android:layout_height="match_parent">

<android.support.design.widget.AppBarLayout
    android:id="@+id/appBar"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">
    <android.support.design.widget.CollapsingToolbarLayout
        android:id="@+id/collapsing_toolbar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:contentScrim="?attr/colorPrimary"
        app:layout_scrollFlags="scroll|enterAlways|snap">

        <RelativeLayout
            android:layout_marginTop="?attr/actionBarSize"
            android:layout_width="match_parent"
            android:layout_height="wrap_content">

            <ImageView
                android:id="@+id/image"
                android:layout_width="match_parent"
                android:layout_height="375dp"
                android:src="@drawable/ic_launcher"/>

            <LinearLayout
                android:layout_marginBottom="30dp"
                android:layout_below="@+id/image"
                android:layout_width="match_parent"
                android:orientation="horizontal"
                android:layout_height="wrap_content">

                <TextView
                    android:layout_marginLeft="30dp"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:textSize="20sp"
                    android:text="textView1"/>

                <TextView
                    android:layout_marginLeft="140dp"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:textSize="20sp"
                    android:text="textView2"/>

            </LinearLayout>

        </RelativeLayout>


        <android.support.v7.widget.Toolbar
            android:id="@+id/mToolbar"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
            app:layout_collapseMode="pin"/>

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

    <LinearLayout
        android:layout_width="match_parent"
        android:orientation="horizontal"
        android:layout_height="wrap_content">

        <TextView
            android:layout_marginLeft="30dp"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="20sp"
            android:text="textView3"/>

        <TextView
            android:layout_marginLeft="140dp"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="20sp"
            android:text="textView4"/>

    </LinearLayout>

    <android.support.design.widget.TabLayout
        android:id="@+id/tabLayout"
        android:layout_width="match_parent"
        android:layout_height="?attr/actionBarSize"
        android:layout_gravity="bottom"
        android:background="?attr/colorPrimary"
        app:tabMode="scrollable"/>
</android.support.design.widget.AppBarLayout>

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

like image 30
David Seroussi Avatar answered Sep 28 '22 01:09

David Seroussi