Home Implementing AppbarLayout scrolling behavior with ScrollView
Post
Cancel

Implementing AppbarLayout scrolling behavior with ScrollView

As there were some bugs in AppbarLayout scrolling behavior, I got the requirement to implement same behavior with scroll view. So here is how we can do it.

Expected Output

Step 1: Not reinventing the wheel

This library is very good as starting point for our final goal, and here you will find detail explanation about how to create this.

Let’s see the basic structure of the this implementation.

<FrameLayout>

    <ImageView
        android:id="@+id/image"
        android:layout_height="240dp" />

    <View
        android:id="@+id/overlay"
        android:layout_height="240dp" />

    <ObservableScrollView android:id="@+id/scroll">

        <LinearLayout android:orientation="vertical">

            <View
                android:id="@+id/paddingtop"
                android:layout_height=“240dp”/>

            <TextView android:id="@+id/main_content" />
        </LinearLayout>
    </ObservableScrollView>

    <LinearLayout
        android:id="@+id/titletext_container"
        android:orientation="vertical">
        android:paddingLeft="@dimen/margin_standard">

        <TextView
            android:id="@+id/title"
            android:minHeight="?attr/actionBarSize" />

        <View
            android:id="@+id/animating_area"
            android:minHeight="184dp" />
    </LinearLayout>

    <FloatingActionButton android:id="@+id/fab" />

</FrameLayout>
  • FrameLayout is used for moving children separately.
  • ImageView(@id/image) is the image that will be translated with parallax effect.
  • View(@id/overlay) is an overlay view.You can see the image is fading in and out. This view overlaps with the image and its opacity is changed by scroll position.

Output

  • ObservableScrollView provide vertical scroll value which is used to scroll other views
  • LinearLayout holds the actual content.
  • View(@id/paddingtop) provide top padding of 240dp so that main content start below header view.
  • TextView(@id/main_content) this represent main content below header.

Output

  • LinearLayout(@id/titletext_container) holds title text and the animating area
  • TextView(@id/titletext) holds title text which will be scaled and translated on top of the action bar, its minimum height is equal to action bar height.
  • View(@id/animating_space) This view provides space for title text to animate. its height is (header height - action bar height).

Output

Step 2: Identifying what need to be done

  • The toolbar should stick at the top.
  • Title text should stick at the top.
  • The status bar should be transparent initially and fade in with the primary color.
  • Image View should start below the status bar.

Step 3: Toolbar should stick at top

  • As Toolbar should be on top of scrolling content, so place it below ObservableScrollView. Also make toolbar transparent initially.
<android.support.v7.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@android:color/transparent"
android:minHeight="?attr/actionBarSize"
app:popupTheme="@style/Theme.AppCompat.Light.DarkActionBar"
app:theme="@style/Toolbar"
/>

Output

  • As we can see title text is overlapping with up icon, this can be corrected by adding left padding of 56dp(toolbar home icon width) to Title text.
<LinearLayout
        android:paddingLeft="@dimen/toolbar_margin_start">
<TextView />
<View />
</LinearLayout>

Output

  • If user scrolled the content more then flexibleRange, change the Toolbar color to primary else keep it transparent.
  @Override
    public void onScrollChanged(int scrollY, boolean firstScroll, boolean dragging) {
    float flexibleRange = mFlexibleSpaceImageHeight - mActionBarSize;
    if(scrollY>=flexibleRange){
    mToolbarView.setBackgroundColor(getResources().getColor(R.color.primary));
    }
    else{
    mToolbarView.setBackgroundColor(Color.TRANSPARENT);
    }
  }

Output

Step 4: Status bar color change

  • From our final output we can see that initially we need to set status bar color as transparent, so in onCreate we can set below code.
  getWindow().setStatusBarColor(Color.TRANSPARENT);
  

But this will result in following output

Output

Basically we need to move image below status bar, this can be done with below code

getWindow().getDecorView().setSystemUiVisibility(
View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN);

Output

You can see Toolbar overlapped with status bar, we need to set top padding to toolbar and it should be of status bar height.

mToolbarView.setPadding(0, getStatusBarHeight(), 0, 0);

Output

But this cause another issue, i.e Toolbar color change will be visible with a flicker as shown below.

Output

This is because we increased action height by adding extra padding but didn’t updated mActionBarSize value so add following

mActionBarSize = getActionBarSize() + getStatusBarHeight();

Output

Step 5: Title text should stick at top

  • Translate Title text till it reaches status bar height, this will stick TextView at top.

Instead of

  
 int titleTranslationY = maxTitleTranslationY - scrollY;

Do this

         int titleTranslationY = Math.max(maxTitleTranslationY - scrollY,getStatusBarHeight());
       

And hear is our final output

Output

You can find the code here

Thanks for reading

This post is licensed under CC BY 4.0 by the author.
Recent Update
Trending Tags
Contents

Trending Tags