FABProgressCircle
FABProgressCircle copied to clipboard
FabProgressCircle cannot collaps if fab is in a CoordinatorLayout
my xml is like this:
<android.support.design.widget.CoordinatorLayout android:id="@+id/rootLayout" 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/app_bar"
android:layout_width="match_parent"
android:layout_height="256dp"
android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">
<android.support.design.widget.CollapsingToolbarLayout
android:id="@+id/collapsingToolbarLayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:contentScrim="?attr/colorPrimary"
app:expandedTitleMarginStart="@dimen/expanded_toolbar_title_margin_start"
app:layout_scrollFlags="scroll|exitUntilCollapsed">
<ImageView
android:id="@+id/ivTripCover"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scaleType="centerCrop"
app:layout_collapseMode="parallax"
app:layout_collapseParallaxMultiplier="0.7"/>
<android.support.v7.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
app:layout_collapseMode="pin"
app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"/>
</android.support.design.widget.CollapsingToolbarLayout>
</android.support.design.widget.AppBarLayout>
<android.support.v7.widget.RecyclerView
android:id="@+id/rvContentList"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
</android.support.v7.widget.RecyclerView>
<com.github.jorgecastilloprz.FABProgressCircle
android:id="@+id/fabProgressCircle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:layout_anchor="@id/app_bar"
app:layout_anchorGravity="bottom|right|end">
<android.support.design.widget.FloatingActionButton
android:id="@+id/fab_sync_play"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="16dp"
android:clickable="true"
android:src="@drawable/ic_backup_white_24dp"
app:layout_anchor="@id/app_bar"
app:layout_anchorGravity="bottom|right|end"
/>
</com.github.jorgecastilloprz.FABProgressCircle>
</android.support.design.widget.CoordinatorLayout>
If I don't use FabProgressCircle, the fab will vanish when toolbar layout is collapsing into a small title bar. However, after I use FabProgressCircle like above, the collapsing animation disappear
This is not really an issue. CoordinatorLayout uses Behaviors to collapse or move anything in it. Any View can have its own Behavior. FloatingActionButton has its Behavior set to collapse.
You should be able to fix this by setting your own custom Behavior manually.
For more information read the documentation: https://developer.android.com/reference/android/support/design/widget/CoordinatorLayout.html
Behaviors
import android.content.Context; import android.os.Build; import android.support.design.widget.CoordinatorLayout; import android.support.v4.view.ViewCompat; import android.support.v4.view.ViewPropertyAnimatorListener; import android.support.v4.view.animation.FastOutSlowInInterpolator; import android.util.AttributeSet; import android.view.View; import android.view.animation.Animation; import android.view.animation.AnimationUtils; import android.view.animation.Interpolator; import android.widget.FrameLayout;
import tatbigy.ultrahd.R;
public class FABProgressCircleBehavior extends CoordinatorLayout.Behavior<FrameLayout> { private static final Interpolator INTERPOLATOR = new FastOutSlowInInterpolator(); private boolean mIsAnimatingOut = false;
public FABProgressCircleBehavior(Context context, AttributeSet attrs) {
super();
}
@Override
public boolean onStartNestedScroll(final CoordinatorLayout coordinatorLayout, final FrameLayout child,
final View directTargetChild, final View target, final int nestedScrollAxes) {
return nestedScrollAxes == ViewCompat.SCROLL_AXIS_VERTICAL
|| super.onStartNestedScroll(coordinatorLayout, child, directTargetChild, target, nestedScrollAxes);
}
@Override
public void onNestedScroll(final CoordinatorLayout coordinatorLayout, final FrameLayout child,
final View target, final int dxConsumed, final int dyConsumed,
final int dxUnconsumed, final int dyUnconsumed) {
super.onNestedScroll(coordinatorLayout, child, target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed);
if (dyConsumed > 0 && !this.mIsAnimatingOut && child.getVisibility() == View.VISIBLE) {
animateOut(child);
} else if (dyConsumed < 0 && child.getVisibility() != View.VISIBLE) {
animateIn(child);
}
}
// Same animation that FloatingActionButton.Behavior uses to hide the FAB when the AppBarLayout exits
private void animateOut(final FrameLayout button) {
if (Build.VERSION.SDK_INT >= 14) {
ViewCompat.animate(button).scaleX(0.0F).scaleY(0.0F).alpha(0.0F).setInterpolator(INTERPOLATOR).withLayer()
.setListener(new ViewPropertyAnimatorListener() {
public void onAnimationStart(View view) {
FABProgressCircleBehavior.this.mIsAnimatingOut = true;
}
public void onAnimationCancel(View view) {
FABProgressCircleBehavior.this.mIsAnimatingOut = false;
}
public void onAnimationEnd(View view) {
FABProgressCircleBehavior.this.mIsAnimatingOut = false;
view.setVisibility(View.GONE);
}
}).start();
} else {
Animation anim = AnimationUtils.loadAnimation(button.getContext(), R.anim.fab_out);
anim.setInterpolator(INTERPOLATOR);
anim.setDuration(200L);
anim.setAnimationListener(new Animation.AnimationListener() {
public void onAnimationStart(Animation animation) {
FABProgressCircleBehavior.this.mIsAnimatingOut = true;
}
public void onAnimationEnd(Animation animation) {
FABProgressCircleBehavior.this.mIsAnimatingOut = false;
button.setVisibility(View.GONE);
}
@Override
public void onAnimationRepeat(final Animation animation) {
}
});
button.startAnimation(anim);
}
}
// Same animation that FloatingActionButton.Behavior uses to show the FAB when the AppBarLayout enters
private void animateIn(FrameLayout button) {
button.setVisibility(View.VISIBLE);
if (Build.VERSION.SDK_INT >= 14) {
ViewCompat.animate(button).scaleX(1.0F).scaleY(1.0F).alpha(1.0F)
.setInterpolator(INTERPOLATOR).withLayer().setListener(null)
.start();
} else {
Animation anim = AnimationUtils.loadAnimation(button.getContext(), R.anim.fab_in);
anim.setDuration(200L);
anim.setInterpolator(INTERPOLATOR);
button.startAnimation(anim);
}
}
}
Can you please post a full sample code of your suggestion? Unfortunately I cannot get it working with the code that is given
I have tried to backport @CoordinatorLayout.DefaultBehavior(FloatingActionButton.Behavior.class), but unsuccessfully. Does anyone succeeded on creating a custom behavior for the FabProgressCircle ?