Skip to content

Instantly share code, notes, and snippets.

@ManuelPeinado
Created October 19, 2014 20:02
Show Gist options
  • Save ManuelPeinado/561748b9fa42d3b25661 to your computer and use it in GitHub Desktop.
Save ManuelPeinado/561748b9fa42d3b25661 to your computer and use it in GitHub Desktop.
Fading action bar effect using the new Toolbar class from the support library
<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:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@null"
tools:context=".MainActivity">
<com.github.manuelpeinado.toolbartest.ObservableScrollView
android:id="@+id/scrollview"
android:text="@string/hello_world"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fillViewport="true">
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<ImageView
android:id="@+id/header"
android:layout_height="wrap_content"
android:layout_width="match_parent"
android:adjustViewBounds="true"
android:src="@drawable/nyc" />
<TextView
android:layout_height="wrap_content"
android:layout_width="match_parent"
android:background="?android:colorBackground"
android:padding="16dp"
android:text="@string/loren_ipsum" />
</LinearLayout>
</com.github.manuelpeinado.toolbartest.ObservableScrollView>
<android.support.v7.widget.Toolbar
android:id="@+id/toolbar"
android:layout_height="wrap_content"
android:layout_width="match_parent"
android:layout_gravity="top"
android:minHeight="?attr/actionBarSize"
android:background="?attr/colorPrimary"
app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
app:popupTheme="@style/ThemeOverlay.AppCompat.Light" />
</FrameLayout>
package com.github.manuelpeinado.toolbartest;
import android.graphics.Color;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.support.v7.widget.Toolbar;
import android.view.Menu;
import android.view.View;
import com.readystatesoftware.systembartint.SystemBarTintManager;
public class MainActivity extends ActionBarActivity implements OnScrollChangedCallback {
private Toolbar mToolbar;
private Drawable mActionBarBackgroundDrawable;
private View mHeader;
private int mLastDampedScroll;
private int mInitialStatusBarColor;
private int mFinalStatusBarColor;
private SystemBarTintManager mStatusBarManager;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mToolbar = (Toolbar) findViewById(R.id.toolbar);
mActionBarBackgroundDrawable = mToolbar.getBackground();
setSupportActionBar(mToolbar);
mStatusBarManager = new SystemBarTintManager(this);
mStatusBarManager.setStatusBarTintEnabled(true);
mInitialStatusBarColor = Color.BLACK;
mFinalStatusBarColor = getResources().getColor(R.color.primary_color_dark);
mHeader = findViewById(R.id.header);
ObservableScrollable scrollView = (ObservableScrollable) findViewById(R.id.scrollview);
scrollView.setOnScrollChangedCallback(this);
onScroll(-1, 0);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
@Override
public void onScroll(int l, int scrollPosition) {
int headerHeight = mHeader.getHeight() - mToolbar.getHeight();
float ratio = 0;
if (scrollPosition > 0 && headerHeight > 0)
ratio = (float) Math.min(Math.max(scrollPosition, 0), headerHeight) / headerHeight;
updateActionBarTransparency(ratio);
updateStatusBarColor(ratio);
updateParallaxEffect(scrollPosition);
}
private void updateActionBarTransparency(float scrollRatio) {
int newAlpha = (int) (scrollRatio * 255);
mActionBarBackgroundDrawable.setAlpha(newAlpha);
mToolbar.setBackground(mActionBarBackgroundDrawable);
}
private void updateStatusBarColor(float scrollRatio) {
int r = interpolate(Color.red(mInitialStatusBarColor), Color.red(mFinalStatusBarColor), 1 - scrollRatio);
int g = interpolate(Color.green(mInitialStatusBarColor), Color.green(mFinalStatusBarColor), 1 - scrollRatio);
int b = interpolate(Color.blue(mInitialStatusBarColor), Color.blue(mFinalStatusBarColor), 1 - scrollRatio);
mStatusBarManager.setTintColor(Color.rgb(r, g, b));
}
private void updateParallaxEffect(int scrollPosition) {
float damping = 0.5f;
int dampedScroll = (int) (scrollPosition * damping);
int offset = mLastDampedScroll - dampedScroll;
mHeader.offsetTopAndBottom(-offset);
mLastDampedScroll = dampedScroll;
}
private int interpolate(int from, int to, float param) {
return (int) (from * param + to * (1 - param));
}
}
<resources>
<style name="AppTheme" parent="Theme.AppCompat.Light">
<item name="windowActionBar">false</item>
<item name="android:windowTranslucentStatus">true</item>
<item name="android:fitsSystemWindows">true</item>
<item name="colorPrimary">@color/primary_color</item>
<item name="colorPrimaryDark">@color/primary_color_dark</item>
<item name="colorAccent">#f77</item>
</style>
</resources>
@MichaelEvans
Copy link

@ramswaroop @nathaliepl : is there any way to do it without those kinds of hacks? Seems messy to have to do that.

@jemshit
Copy link

jemshit commented Mar 8, 2015

What is min API supported, 11?

@danielwilson1702
Copy link

Hmm I have quite a complicated list view and can't get this to work (instead of a scroll view), is there any example anywhere?

@AdarshYadav
Copy link

As per my requirement I have to fix a button at the bottom of the screen,which is visible for all the time so I putted it out of scroll-view. But after doing this I found that there is no fading effect only content inside scroll-view is scroll able even header image-view also stops scrolling. Anyone have any idea why it's not working?

@aniruddhasm
Copy link

Thanks @ManuelPeinado with this example.
Here is solution to all your problems.

parallax effect on RecyclerView == https://github.com/kanytu/android-parallax-recyclerview

parallax listview, scrollview and gridview with zoom support == https://github.com/kanytu/android-parallax-listview

@Adnan9011
Copy link

finally i solve this
do this things 😄

  1. Copy Java Code
  2. Copy Xml Layout
  3. replace com.github.manuelpeinado.toolbartest.ObservableScrollView to com.manuelpeinado.fadingactionbar.view.ObservableScrollView
  4. add FadingActionBar library at https://g"ithub.com/ManuelPeinado/
  5. add https://github.com/jgilfelt/SystemBarTint library
  6. copy Style recource
  7. add this for appcompat 22.2 :
    http://stackoverflow.com/questions/29784124/java-lang-illegalargumentexception-appcompat-does-not-support-the-current-theme
  8. enjoy it 😊

@sumitsharmadesi
Copy link

When redirected to next activity and come back header layout becomes invisible. How to solve this ?

@rciovati
Copy link

FYI: It's also possible to use the android.support.v4.widget.NestedScrollView bundled in the support library instead of com.github.manuelpeinado.toolbartest.ObservableScrollView.

@gosuka
Copy link

gosuka commented Dec 2, 2015

I'm having the same issue with @ramswaroop, when I go back, the action opacity doesn't return to normal

@anubhav17
Copy link

@nathaliepl thanks for your help it solved my issue.In parent activity just needed to ad this code

public void onResume(){
    super.onResume();
    updateColor();

}

@TargetApi(Build.VERSION_CODES.JELLY_BEAN)
private void updateColor() {
    toolbarBackgroundDrawable.setAlpha(255); // 0% of transparency
    toolbar.setBackground(toolbarBackgroundDrawable);
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment