Example usage for android.view View TRANSLATION_Z

List of usage examples for android.view View TRANSLATION_Z

Introduction

In this page you can find the example usage for android.view View TRANSLATION_Z.

Prototype

Property TRANSLATION_Z

To view the source code for android.view View TRANSLATION_Z.

Click Source Link

Document

A Property wrapper around the translationZ functionality handled by the View#setTranslationZ(float) and View#getTranslationZ() methods.

Usage

From source file:com.commonsware.cwac.crossport.design.widget.FloatingActionButtonLollipop.java

@Override
void onElevationsChanged(final float elevation, final float pressedTranslationZ) {
    if (Build.VERSION.SDK_INT == 21) {
        // Animations produce NPE in version 21. Bluntly set the values instead (matching the
        // logic in the animations below).
        if (mView.isEnabled()) {
            mView.setElevation(elevation);
            if (mView.isFocused() || mView.isPressed()) {
                mView.setTranslationZ(pressedTranslationZ);
            } else {
                mView.setTranslationZ(0);
            }/*  w w  w.java 2  s. c  om*/
        } else {
            mView.setElevation(0);
            mView.setTranslationZ(0);
        }
    } else {
        final StateListAnimator stateListAnimator = new StateListAnimator();

        // Animate elevation and translationZ to our values when pressed
        AnimatorSet set = new AnimatorSet();
        set.play(ObjectAnimator.ofFloat(mView, "elevation", elevation).setDuration(0)).with(ObjectAnimator
                .ofFloat(mView, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(PRESSED_ENABLED_STATE_SET, set);

        // Same deal for when we're focused
        set = new AnimatorSet();
        set.play(ObjectAnimator.ofFloat(mView, "elevation", elevation).setDuration(0)).with(ObjectAnimator
                .ofFloat(mView, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(FOCUSED_ENABLED_STATE_SET, set);

        // Animate translationZ to 0 if not pressed
        set = new AnimatorSet();
        List<Animator> animators = new ArrayList<>();
        animators.add(ObjectAnimator.ofFloat(mView, "elevation", elevation).setDuration(0));
        if (Build.VERSION.SDK_INT >= 22 && Build.VERSION.SDK_INT <= 24) {
            // This is a no-op animation which exists here only for introducing the duration
            // because setting the delay (on the next animation) via "setDelay" or "after"
            // can trigger a NPE between android versions 22 and 24 (due to a framework
            // bug). The issue has been fixed in version 25.
            animators.add(ObjectAnimator.ofFloat(mView, View.TRANSLATION_Z, mView.getTranslationZ())
                    .setDuration(PRESSED_ANIM_DELAY));
        }
        animators.add(ObjectAnimator.ofFloat(mView, View.TRANSLATION_Z, 0f).setDuration(PRESSED_ANIM_DURATION));
        set.playSequentially(animators.toArray(new ObjectAnimator[0]));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(ENABLED_STATE_SET, set);

        // Animate everything to 0 when disabled
        set = new AnimatorSet();
        set.play(ObjectAnimator.ofFloat(mView, "elevation", 0f).setDuration(0))
                .with(ObjectAnimator.ofFloat(mView, View.TRANSLATION_Z, 0f).setDuration(0));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(EMPTY_STATE_SET, set);

        mView.setStateListAnimator(stateListAnimator);
    }

    if (mShadowViewDelegate.isCompatPaddingEnabled()) {
        updatePadding();
    }
}

From source file:android.support.design.widget.FloatingActionButtonLollipop.java

@Override
void onElevationsChanged(final float elevation, final float pressedTranslationZ) {
    final int sdk = Build.VERSION.SDK_INT;
    if (sdk == 21) {
        // Animations produce NPE in version 21. Bluntly set the values instead (matching the
        // logic in the animations below).
        if (mView.isEnabled()) {
            mView.setElevation(elevation);
            if (mView.isFocused() || mView.isPressed()) {
                mView.setTranslationZ(pressedTranslationZ);
            } else {
                mView.setTranslationZ(0);
            }/*from  w  w w  . j  a v  a2s.com*/
        } else {
            mView.setElevation(0);
            mView.setTranslationZ(0);
        }
    } else {
        final StateListAnimator stateListAnimator = new StateListAnimator();

        // Animate elevation and translationZ to our values when pressed
        AnimatorSet set = new AnimatorSet();
        set.play(ObjectAnimator.ofFloat(mView, "elevation", elevation).setDuration(0)).with(ObjectAnimator
                .ofFloat(mView, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(PRESSED_ENABLED_STATE_SET, set);

        // Same deal for when we're focused
        set = new AnimatorSet();
        set.play(ObjectAnimator.ofFloat(mView, "elevation", elevation).setDuration(0)).with(ObjectAnimator
                .ofFloat(mView, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(FOCUSED_ENABLED_STATE_SET, set);

        // Animate translationZ to 0 if not pressed
        set = new AnimatorSet();
        set.playSequentially(ObjectAnimator.ofFloat(mView, "elevation", elevation).setDuration(0),
                // This is a no-op animation which exists here only for introducing the duration
                // because setting the delay (on the next animation) via "setDelay" or "after"
                // can trigger a NPE between android versions 22 and 24 (due to a framework
                // bug). The issue has been fixed in version 25.
                ObjectAnimator.ofFloat(mView, View.TRANSLATION_Z, mView.getTranslationZ())
                        .setDuration(PRESSED_ANIM_DELAY),
                ObjectAnimator.ofFloat(mView, View.TRANSLATION_Z, 0f).setDuration(PRESSED_ANIM_DURATION));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(ENABLED_STATE_SET, set);

        // Animate everything to 0 when disabled
        set = new AnimatorSet();
        set.play(ObjectAnimator.ofFloat(mView, "elevation", 0f).setDuration(0))
                .with(ObjectAnimator.ofFloat(mView, View.TRANSLATION_Z, 0f).setDuration(0));
        set.setInterpolator(ANIM_INTERPOLATOR);
        stateListAnimator.addState(EMPTY_STATE_SET, set);

        mView.setStateListAnimator(stateListAnimator);
    }

    if (mShadowViewDelegate.isCompatPaddingEnabled()) {
        updatePadding();
    }
}

From source file:com.bartoszlipinski.viewpropertyobjectanimator.ViewPropertyObjectAnimator.java

@SuppressLint("NewApi")
public ViewPropertyObjectAnimator translationZ(float translationZ) {
    if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
        animateProperty(View.TRANSLATION_Z, translationZ);
    }/*from   ww w  .  java  2 s .  co  m*/
    return this;
}

From source file:com.bartoszlipinski.viewpropertyobjectanimator.ViewPropertyObjectAnimator.java

@SuppressLint("NewApi")
public ViewPropertyObjectAnimator translationZBy(float translationZBy) {
    if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
        animatePropertyBy(View.TRANSLATION_Z, translationZBy);
    }//from   w w w.  j  ava2 s .  c  om
    return this;
}

From source file:com.myhexaville.iconanimations.gooey_fab.GooeyFab.java

void onElevationsChanged(final float elevation, final float pressedTranslationZ) {
    final StateListAnimator stateListAnimator = new StateListAnimator();

    // Animate elevation and translationZ to our values when pressed
    AnimatorSet set = new AnimatorSet();
    set.play(ObjectAnimator.ofFloat(this, "elevation", elevation).setDuration(0)).with(ObjectAnimator
            .ofFloat(this, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(PRESSED_ENABLED_STATE_SET, set);

    // Same deal for when we're focused
    set = new AnimatorSet();
    set.play(ObjectAnimator.ofFloat(this, "elevation", elevation).setDuration(0)).with(ObjectAnimator
            .ofFloat(this, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(FOCUSED_ENABLED_STATE_SET, set);

    // Animate translationZ to 0 if not pressed
    set = new AnimatorSet();
    // Use an AnimatorSet to set a start delay since there is a bug with ValueAnimator that
    // prevents it from being cancelled properly when used with a StateListAnimator.
    AnimatorSet anim = new AnimatorSet();
    anim.play(ObjectAnimator.ofFloat(this, View.TRANSLATION_Z, 0f).setDuration(PRESSED_ANIM_DURATION))
            .after(PRESSED_ANIM_DURATION);
    set.play(ObjectAnimator.ofFloat(this, "elevation", elevation).setDuration(0)).with(anim);
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(ENABLED_STATE_SET, set);

    // Animate everything to 0 when disabled
    set = new AnimatorSet();
    set.play(ObjectAnimator.ofFloat(this, "elevation", 0f).setDuration(0))
            .with(ObjectAnimator.ofFloat(this, View.TRANSLATION_Z, 0f).setDuration(0));
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(EMPTY_STATE_SET, set);

    setStateListAnimator(stateListAnimator);
}

From source file:com.myhexaville.iconanimations.gooey_fab.GooeyFabCompatImpl.java

@TargetApi(21)
void onElevationsChanged(final float elevation, final float pressedTranslationZ) {
    final StateListAnimator stateListAnimator = new StateListAnimator();

    // Animate elevation and translationZ to our values when pressed
    AnimatorSet set = new AnimatorSet();
    set.play(ObjectAnimator.ofFloat(this, "elevation", elevation).setDuration(0)).with(ObjectAnimator
            .ofFloat(this, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(PRESSED_ENABLED_STATE_SET, set);

    // Same deal for when we're focused
    set = new AnimatorSet();
    set.play(ObjectAnimator.ofFloat(this, "elevation", elevation).setDuration(0)).with(ObjectAnimator
            .ofFloat(this, View.TRANSLATION_Z, pressedTranslationZ).setDuration(PRESSED_ANIM_DURATION));
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(FOCUSED_ENABLED_STATE_SET, set);

    // Animate translationZ to 0 if not pressed
    set = new AnimatorSet();
    // Use an AnimatorSet to set a start delay since there is a bug with ValueAnimator that
    // prevents it from being cancelled properly when used with a StateListAnimator.
    AnimatorSet anim = new AnimatorSet();
    anim.play(ObjectAnimator.ofFloat(this, View.TRANSLATION_Z, 0f).setDuration(PRESSED_ANIM_DURATION))
            .after(PRESSED_ANIM_DURATION);
    set.play(ObjectAnimator.ofFloat(this, "elevation", elevation).setDuration(0)).with(anim);
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(ENABLED_STATE_SET, set);

    // Animate everything to 0 when disabled
    set = new AnimatorSet();
    set.play(ObjectAnimator.ofFloat(this, "elevation", 0f).setDuration(0))
            .with(ObjectAnimator.ofFloat(this, View.TRANSLATION_Z, 0f).setDuration(0));
    set.setInterpolator(ANIM_INTERPOLATOR);
    stateListAnimator.addState(EMPTY_STATE_SET, set);

    setStateListAnimator(stateListAnimator);
}

From source file:de.dreier.mytargets.utils.transitions.FabTransform.java

@Override
public Animator createAnimator(@NonNull final ViewGroup sceneRoot, final TransitionValues startValues,
        final TransitionValues endValues) {
    if (startValues == null || endValues == null) {
        return null;
    }/*from ww w.  j av a  2 s.  c  om*/

    final Rect startBounds = (Rect) startValues.values.get(PROP_BOUNDS);
    final Rect endBounds = (Rect) endValues.values.get(PROP_BOUNDS);

    final boolean fromFab = endBounds.width() > startBounds.width();
    final View view = endValues.view;
    final Rect dialogBounds = fromFab ? endBounds : startBounds;
    final Rect fabBounds = fromFab ? startBounds : endBounds;
    final Interpolator fastOutSlowInInterpolator = new FastOutSlowInInterpolator();
    final long duration = getDuration();
    final long halfDuration = duration / 2;
    final long twoThirdsDuration = duration * 2 / 3;

    if (!fromFab) {
        // Force measure / layout the dialog back to it's original bounds
        view.measure(makeMeasureSpec(startBounds.width(), View.MeasureSpec.EXACTLY),
                makeMeasureSpec(startBounds.height(), View.MeasureSpec.EXACTLY));
        view.layout(startBounds.left, startBounds.top, startBounds.right, startBounds.bottom);
    }

    final int translationX = startBounds.centerX() - endBounds.centerX();
    final int translationY = startBounds.centerY() - endBounds.centerY();
    if (fromFab) {
        view.setTranslationX(translationX);
        view.setTranslationY(translationY);
    }

    // Add a color overlay to fake appearance of the FAB
    final ColorDrawable fabColor = new ColorDrawable(color);
    fabColor.setBounds(0, 0, dialogBounds.width(), dialogBounds.height());
    if (!fromFab) {
        fabColor.setAlpha(0);
    }
    view.getOverlay().add(fabColor);

    // Add an icon overlay again to fake the appearance of the FAB
    final Drawable fabIcon = ContextCompat.getDrawable(sceneRoot.getContext(), icon).mutate();
    final int iconLeft = (dialogBounds.width() - fabIcon.getIntrinsicWidth()) / 2;
    final int iconTop = (dialogBounds.height() - fabIcon.getIntrinsicHeight()) / 2;
    fabIcon.setBounds(iconLeft, iconTop, iconLeft + fabIcon.getIntrinsicWidth(),
            iconTop + fabIcon.getIntrinsicHeight());
    if (!fromFab) {
        fabIcon.setAlpha(0);
    }
    view.getOverlay().add(fabIcon);

    // Circular clip from/to the FAB size
    final Animator circularReveal;
    if (fromFab) {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, startBounds.width() / 2,
                (float) Math.hypot(endBounds.width() / 2, endBounds.height() / 2));
        circularReveal.setInterpolator(new FastOutLinearInInterpolator());
    } else {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, (float) Math.hypot(startBounds.width() / 2, startBounds.height() / 2),
                endBounds.width() / 2);
        circularReveal.setInterpolator(new LinearOutSlowInInterpolator());

        // Persist the end clip i.e. stay at FAB size after the reveal has run
        circularReveal.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                view.setOutlineProvider(new ViewOutlineProvider() {
                    @Override
                    public void getOutline(View view, Outline outline) {
                        final int left = (view.getWidth() - fabBounds.width()) / 2;
                        final int top = (view.getHeight() - fabBounds.height()) / 2;
                        outline.setOval(left, top, left + fabBounds.width(), top + fabBounds.height());
                        view.setClipToOutline(true);
                    }
                });
            }
        });
    }
    circularReveal.setDuration(duration);

    // Translate to end position along an arc
    final Animator translate = ObjectAnimator.ofFloat(view, View.TRANSLATION_X, View.TRANSLATION_Y,
            fromFab ? getPathMotion().getPath(translationX, translationY, 0, 0)
                    : getPathMotion().getPath(0, 0, -translationX, -translationY));
    translate.setDuration(duration);
    translate.setInterpolator(fastOutSlowInInterpolator);

    // Fade contents of non-FAB view in/out
    List<Animator> fadeContents = null;
    if (view instanceof ViewGroup) {
        final ViewGroup vg = ((ViewGroup) view);
        fadeContents = new ArrayList<>(vg.getChildCount());
        for (int i = vg.getChildCount() - 1; i >= 0; i--) {
            final View child = vg.getChildAt(i);
            final Animator fade = ObjectAnimator.ofFloat(child, View.ALPHA, fromFab ? 1f : 0f);
            if (fromFab) {
                child.setAlpha(0f);
            }
            fade.setDuration(twoThirdsDuration);
            fade.setInterpolator(fastOutSlowInInterpolator);
            fadeContents.add(fade);
        }
    }

    // Fade in/out the fab color & icon overlays
    final Animator colorFade = ObjectAnimator.ofInt(fabColor, "alpha", fromFab ? 0 : 255);
    final Animator iconFade = ObjectAnimator.ofInt(fabIcon, "alpha", fromFab ? 0 : 255);
    if (!fromFab) {
        colorFade.setStartDelay(halfDuration);
        iconFade.setStartDelay(halfDuration);
    }
    colorFade.setDuration(halfDuration);
    iconFade.setDuration(halfDuration);
    colorFade.setInterpolator(fastOutSlowInInterpolator);
    iconFade.setInterpolator(fastOutSlowInInterpolator);

    // Work around issue with elevation shadows. At the end of the return transition the shared
    // element's shadow is drawn twice (by each activity) which is jarring. This workaround
    // still causes the shadow to snap, but it's better than seeing it double drawn.
    Animator elevation = null;
    if (!fromFab) {
        elevation = ObjectAnimator.ofFloat(view, View.TRANSLATION_Z, -view.getElevation());
        elevation.setDuration(duration);
        elevation.setInterpolator(fastOutSlowInInterpolator);
    }

    // Run all animations together
    final AnimatorSet transition = new AnimatorSet();
    transition.playTogether(circularReveal, translate, colorFade, iconFade);
    transition.playTogether(fadeContents);
    if (elevation != null) {
        transition.play(elevation);
    }
    if (fromFab) {
        transition.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                // Clean up
                view.getOverlay().clear();
            }
        });
    }
    return new NoPauseAnimator(transition);
}

From source file:com.n3rditorium.pocketdoggie.transitions.FabTransform.java

@Override
public Animator createAnimator(final ViewGroup sceneRoot, final TransitionValues startValues,
        final TransitionValues endValues) {
    if (startValues == null || endValues == null) {
        return null;
    }/* w w  w .  j  a va  2s.  c o  m*/

    final Rect startBounds = (Rect) startValues.values.get(PROP_BOUNDS);
    final Rect endBounds = (Rect) endValues.values.get(PROP_BOUNDS);

    final boolean fromFab = endBounds.width() > startBounds.width();
    final View view = endValues.view;
    final Rect dialogBounds = fromFab ? endBounds : startBounds;
    final Rect fabBounds = fromFab ? startBounds : endBounds;
    final Interpolator fastOutSlowInInterpolator = AnimUtils
            .getFastOutSlowInInterpolator(sceneRoot.getContext());
    final long duration = getDuration();
    final long halfDuration = duration / 2;
    final long twoThirdsDuration = duration * 2 / 3;

    if (!fromFab) {
        // Force measure / layout the dialog back to it's original bounds
        view.measure(makeMeasureSpec(startBounds.width(), View.MeasureSpec.EXACTLY),
                makeMeasureSpec(startBounds.height(), View.MeasureSpec.EXACTLY));
        view.layout(startBounds.left, startBounds.top, startBounds.right, startBounds.bottom);
    }

    final int translationX = startBounds.centerX() - endBounds.centerX();
    final int translationY = startBounds.centerY() - endBounds.centerY();
    if (fromFab) {
        view.setTranslationX(translationX);
        view.setTranslationY(translationY);
    }

    // Add a color overlay to fake appearance of the FAB
    final ColorDrawable fabColor = new ColorDrawable(color);
    fabColor.setBounds(0, 0, dialogBounds.width(), dialogBounds.height());
    if (!fromFab) {
        fabColor.setAlpha(0);
    }
    view.getOverlay().add(fabColor);

    // Add an icon overlay again to fake the appearance of the FAB
    final Drawable fabIcon = ContextCompat.getDrawable(sceneRoot.getContext(), icon).mutate();
    final int iconLeft = (dialogBounds.width() - fabIcon.getIntrinsicWidth()) / 2;
    final int iconTop = (dialogBounds.height() - fabIcon.getIntrinsicHeight()) / 2;
    fabIcon.setBounds(iconLeft, iconTop, iconLeft + fabIcon.getIntrinsicWidth(),
            iconTop + fabIcon.getIntrinsicHeight());
    if (!fromFab) {
        fabIcon.setAlpha(0);
    }
    view.getOverlay().add(fabIcon);

    // Circular clip from/to the FAB size
    final Animator circularReveal;
    if (fromFab) {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, startBounds.width() / 2,
                (float) Math.hypot(endBounds.width() / 2, endBounds.width() / 2));
        circularReveal.setInterpolator(AnimUtils.getFastOutLinearInInterpolator(sceneRoot.getContext()));
    } else {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, (float) Math.hypot(startBounds.width() / 2, startBounds.width() / 2),
                endBounds.width() / 2);
        circularReveal.setInterpolator(AnimUtils.getLinearOutSlowInInterpolator(sceneRoot.getContext()));

        // Persist the end clip i.e. stay at FAB size after the reveal has run
        circularReveal.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                view.setOutlineProvider(new ViewOutlineProvider() {
                    @Override
                    public void getOutline(View view, Outline outline) {
                        final int left = (view.getWidth() - fabBounds.width()) / 2;
                        final int top = (view.getHeight() - fabBounds.height()) / 2;
                        outline.setOval(left, top, left + fabBounds.width(), top + fabBounds.height());
                        view.setClipToOutline(true);
                    }
                });
            }
        });
    }
    circularReveal.setDuration(duration);

    // Translate to end position along an arc
    final Animator translate = ObjectAnimator.ofFloat(view, View.TRANSLATION_X, View.TRANSLATION_Y,
            fromFab ? getPathMotion().getPath(translationX, translationY, 0, 0)
                    : getPathMotion().getPath(0, 0, -translationX, -translationY));
    translate.setDuration(duration);
    translate.setInterpolator(fastOutSlowInInterpolator);

    // Fade contents of non-FAB view in/out
    List<Animator> fadeContents = null;
    if (view instanceof ViewGroup) {
        final ViewGroup vg = ((ViewGroup) view);
        fadeContents = new ArrayList<>(vg.getChildCount());
        for (int i = vg.getChildCount() - 1; i >= 0; i--) {
            final View child = vg.getChildAt(i);
            final Animator fade = ObjectAnimator.ofFloat(child, View.ALPHA, fromFab ? 1f : 0f);
            if (fromFab) {
                child.setAlpha(0f);
            }
            fade.setDuration(twoThirdsDuration);
            fade.setInterpolator(fastOutSlowInInterpolator);
            fadeContents.add(fade);
        }
    }

    // Fade in/out the fab color & icon overlays
    final Animator colorFade = ObjectAnimator.ofInt(fabColor, "alpha", fromFab ? 0 : 255);
    final Animator iconFade = ObjectAnimator.ofInt(fabIcon, "alpha", fromFab ? 0 : 255);
    if (!fromFab) {
        colorFade.setStartDelay(halfDuration);
        iconFade.setStartDelay(halfDuration);
    }
    colorFade.setDuration(halfDuration);
    iconFade.setDuration(halfDuration);
    colorFade.setInterpolator(fastOutSlowInInterpolator);
    iconFade.setInterpolator(fastOutSlowInInterpolator);

    // Work around issue with elevation shadows. At the end of the return transition the shared
    // element's shadow is drawn twice (by each activity) which is jarring. This workaround
    // still causes the shadow to snap, but it's better than seeing it double drawn.
    Animator elevation = null;
    if (!fromFab) {
        elevation = ObjectAnimator.ofFloat(view, View.TRANSLATION_Z, -view.getElevation());
        elevation.setDuration(duration);
        elevation.setInterpolator(fastOutSlowInInterpolator);
    }

    // Run all animations together
    final AnimatorSet transition = new AnimatorSet();
    transition.playTogether(circularReveal, translate, colorFade, iconFade);
    transition.playTogether(fadeContents);
    if (elevation != null) {
        transition.play(elevation);
    }
    if (fromFab) {
        transition.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                // Clean up
                view.getOverlay().clear();
            }
        });
    }
    return new AnimUtils.NoPauseAnimator(transition);
}

From source file:com.hitomi.circlemenu.transtion.FabTransform.java

@Override
public Animator createAnimator(final ViewGroup sceneRoot, final TransitionValues startValues,
        final TransitionValues endValues) {
    if (startValues == null || endValues == null)
        return null;

    final Rect startBounds = (Rect) startValues.values.get(PROP_BOUNDS);
    final Rect endBounds = (Rect) endValues.values.get(PROP_BOUNDS);

    final boolean fromFab = endBounds.width() > startBounds.width();
    final View view = endValues.view;
    final Rect dialogBounds = fromFab ? endBounds : startBounds;
    final Rect fabBounds = fromFab ? startBounds : endBounds;
    final Interpolator fastOutSlowInInterpolator = AnimUtils
            .getFastOutSlowInInterpolator(sceneRoot.getContext());
    final long duration = getDuration();
    final long halfDuration = duration / 2;
    final long twoThirdsDuration = duration * 2 / 3;

    if (!fromFab) {
        // Force measure / layout the dialog back to it'page_two original bounds
        view.measure(makeMeasureSpec(startBounds.width(), View.MeasureSpec.EXACTLY),
                makeMeasureSpec(startBounds.height(), View.MeasureSpec.EXACTLY));
        view.layout(startBounds.left, startBounds.top, startBounds.right, startBounds.bottom);
    }// w ww  .jav a  2  s  .  c o  m

    final int translationX = startBounds.centerX() - endBounds.centerX();
    final int translationY = startBounds.centerY() - endBounds.centerY();
    if (fromFab) {
        view.setTranslationX(translationX);
        view.setTranslationY(translationY);
    }

    // Add a color overlay to fake appearance of the FAB
    final ColorDrawable fabColor = new ColorDrawable(color);
    fabColor.setBounds(0, 0, dialogBounds.width(), dialogBounds.height());
    if (!fromFab)
        fabColor.setAlpha(0);
    view.getOverlay().add(fabColor);

    // Add an icon overlay again to fake the appearance of the FAB
    final Drawable fabIcon = ContextCompat.getDrawable(sceneRoot.getContext(), icon).mutate();
    final int iconLeft = (dialogBounds.width() - fabIcon.getIntrinsicWidth()) / 2;
    final int iconTop = (dialogBounds.height() - fabIcon.getIntrinsicHeight()) / 2;
    fabIcon.setBounds(iconLeft, iconTop, iconLeft + fabIcon.getIntrinsicWidth(),
            iconTop + fabIcon.getIntrinsicHeight());
    if (!fromFab)
        fabIcon.setAlpha(0);
    view.getOverlay().add(fabIcon);

    // Circular clip from/to the FAB size
    final Animator circularReveal;
    if (fromFab) {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, startBounds.width() / 2,
                (float) Math.hypot(endBounds.width() / 2, endBounds.height() / 2));
        circularReveal.setInterpolator(AnimUtils.getFastOutLinearInInterpolator(sceneRoot.getContext()));
    } else {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, (float) Math.hypot(startBounds.width() / 2, startBounds.height() / 2),
                endBounds.width() / 2);
        circularReveal.setInterpolator(AnimUtils.getLinearOutSlowInInterpolator(sceneRoot.getContext()));

        // Persist the end clip i.e. stay at FAB size after the reveal has run
        circularReveal.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                view.setOutlineProvider(new ViewOutlineProvider() {
                    @Override
                    public void getOutline(View view, Outline outline) {
                        final int left = (view.getWidth() - fabBounds.width()) / 2;
                        final int top = (view.getHeight() - fabBounds.height()) / 2;
                        outline.setOval(left, top, left + fabBounds.width(), top + fabBounds.height());
                        view.setClipToOutline(true);
                    }
                });
            }
        });
    }
    circularReveal.setDuration(duration);

    // Translate to end position along an arc
    final Animator translate = ObjectAnimator.ofFloat(view, View.TRANSLATION_X, View.TRANSLATION_Y,
            fromFab ? getPathMotion().getPath(translationX, translationY, 0, 0)
                    : getPathMotion().getPath(0, 0, -translationX, -translationY));
    translate.setDuration(duration);
    translate.setInterpolator(fastOutSlowInInterpolator);

    // Fade contents of non-FAB view in/out
    List<Animator> fadeContents = null;
    if (view instanceof ViewGroup) {
        final ViewGroup vg = ((ViewGroup) view);
        fadeContents = new ArrayList<>(vg.getChildCount());
        for (int i = vg.getChildCount() - 1; i >= 0; i--) {
            final View child = vg.getChildAt(i);
            final Animator fade = ObjectAnimator.ofFloat(child, View.ALPHA, fromFab ? 1f : 0f);
            if (fromFab) {
                child.setAlpha(0f);
            }
            fade.setDuration(twoThirdsDuration);
            fade.setInterpolator(fastOutSlowInInterpolator);
            fadeContents.add(fade);
        }
    }

    // Fade in/out the fab color & icon overlays
    final Animator colorFade = ObjectAnimator.ofInt(fabColor, "alpha", fromFab ? 0 : 255);
    final Animator iconFade = ObjectAnimator.ofInt(fabIcon, "alpha", fromFab ? 0 : 255);
    if (!fromFab) {
        colorFade.setStartDelay(halfDuration);
        iconFade.setStartDelay(halfDuration);
    }
    colorFade.setDuration(halfDuration);
    iconFade.setDuration(halfDuration);
    colorFade.setInterpolator(fastOutSlowInInterpolator);
    iconFade.setInterpolator(fastOutSlowInInterpolator);

    // Work around issue with elevation shadows. At the end of the return transition the shared
    // element'page_two shadow is drawn twice (by each activity) which is jarring. This workaround
    // still causes the shadow to snap, but it'page_two better than seeing it double drawn.
    Animator elevation = null;
    if (!fromFab) {
        elevation = ObjectAnimator.ofFloat(view, View.TRANSLATION_Z, -view.getElevation());
        elevation.setDuration(duration);
        elevation.setInterpolator(fastOutSlowInInterpolator);
    }

    // Run all animations together
    final AnimatorSet transition = new AnimatorSet();
    transition.playTogether(circularReveal, translate, colorFade, iconFade);
    transition.playTogether(fadeContents);
    if (elevation != null)
        transition.play(elevation);
    if (fromFab) {
        transition.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                // Clean up
                view.getOverlay().clear();
            }
        });
    }
    return new AnimUtils.NoPauseAnimator(transition);
}

From source file:com.amitupadhyay.aboutexample.ui.transitions.FabTransform.java

@Override
public Animator createAnimator(final ViewGroup sceneRoot, final TransitionValues startValues,
        final TransitionValues endValues) {
    if (startValues == null || endValues == null)
        return null;

    final Rect startBounds = (Rect) startValues.values.get(PROP_BOUNDS);
    final Rect endBounds = (Rect) endValues.values.get(PROP_BOUNDS);

    final boolean fromFab = endBounds.width() > startBounds.width();
    final View view = endValues.view;
    final Rect dialogBounds = fromFab ? endBounds : startBounds;
    final Rect fabBounds = fromFab ? startBounds : endBounds;
    final Interpolator fastOutSlowInInterpolator = AnimUtils
            .getFastOutSlowInInterpolator(sceneRoot.getContext());
    final long duration = getDuration();
    final long halfDuration = duration / 2;
    final long twoThirdsDuration = duration * 2 / 3;

    if (!fromFab) {
        // Force measure / layout the dialog back to it's original bounds
        view.measure(makeMeasureSpec(startBounds.width(), View.MeasureSpec.EXACTLY),
                makeMeasureSpec(startBounds.height(), View.MeasureSpec.EXACTLY));
        view.layout(startBounds.left, startBounds.top, startBounds.right, startBounds.bottom);
    }//from w w w. j  a v a2 s.  c o  m

    final int translationX = startBounds.centerX() - endBounds.centerX();
    final int translationY = startBounds.centerY() - endBounds.centerY();
    if (fromFab) {
        view.setTranslationX(translationX);
        view.setTranslationY(translationY);
    }

    // Add a color overlay to fake appearance of the FAB
    final ColorDrawable fabColor = new ColorDrawable(color);
    fabColor.setBounds(0, 0, dialogBounds.width(), dialogBounds.height());
    if (!fromFab)
        fabColor.setAlpha(0);
    view.getOverlay().add(fabColor);

    // Add an icon overlay again to fake the appearance of the FAB
    final Drawable fabIcon = ContextCompat.getDrawable(sceneRoot.getContext(), icon).mutate();
    final int iconLeft = (dialogBounds.width() - fabIcon.getIntrinsicWidth()) / 2;
    final int iconTop = (dialogBounds.height() - fabIcon.getIntrinsicHeight()) / 2;
    fabIcon.setBounds(iconLeft, iconTop, iconLeft + fabIcon.getIntrinsicWidth(),
            iconTop + fabIcon.getIntrinsicHeight());
    if (!fromFab)
        fabIcon.setAlpha(0);
    view.getOverlay().add(fabIcon);

    // Circular clip from/to the FAB size
    final Animator circularReveal;
    if (fromFab) {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, startBounds.width() / 2,
                (float) Math.hypot(endBounds.width() / 2, endBounds.height() / 2));
        circularReveal.setInterpolator(AnimUtils.getFastOutLinearInInterpolator(sceneRoot.getContext()));
    } else {
        circularReveal = ViewAnimationUtils.createCircularReveal(view, view.getWidth() / 2,
                view.getHeight() / 2, (float) Math.hypot(startBounds.width() / 2, startBounds.height() / 2),
                endBounds.width() / 2);
        circularReveal.setInterpolator(AnimUtils.getLinearOutSlowInInterpolator(sceneRoot.getContext()));

        // Persist the end clip i.e. stay at FAB size after the reveal has run
        circularReveal.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                view.setOutlineProvider(new ViewOutlineProvider() {
                    @Override
                    public void getOutline(View view, Outline outline) {
                        final int left = (view.getWidth() - fabBounds.width()) / 2;
                        final int top = (view.getHeight() - fabBounds.height()) / 2;
                        outline.setOval(left, top, left + fabBounds.width(), top + fabBounds.height());
                        view.setClipToOutline(true);
                    }
                });
            }
        });
    }
    circularReveal.setDuration(duration);

    // Translate to end position along an arc
    final Animator translate = ObjectAnimator.ofFloat(view, View.TRANSLATION_X, View.TRANSLATION_Y,
            fromFab ? getPathMotion().getPath(translationX, translationY, 0, 0)
                    : getPathMotion().getPath(0, 0, -translationX, -translationY));
    translate.setDuration(duration);
    translate.setInterpolator(fastOutSlowInInterpolator);

    // Fade contents of non-FAB view in/out
    List<Animator> fadeContents = null;
    if (view instanceof ViewGroup) {
        final ViewGroup vg = ((ViewGroup) view);
        fadeContents = new ArrayList<>(vg.getChildCount());
        for (int i = vg.getChildCount() - 1; i >= 0; i--) {
            final View child = vg.getChildAt(i);
            final Animator fade = ObjectAnimator.ofFloat(child, View.ALPHA, fromFab ? 1f : 0f);
            if (fromFab) {
                child.setAlpha(0f);
            }
            fade.setDuration(twoThirdsDuration);
            fade.setInterpolator(fastOutSlowInInterpolator);
            fadeContents.add(fade);
        }
    }

    // Fade in/out the fab color & icon overlays
    final Animator colorFade = ObjectAnimator.ofInt(fabColor, "alpha", fromFab ? 0 : 255);
    final Animator iconFade = ObjectAnimator.ofInt(fabIcon, "alpha", fromFab ? 0 : 255);
    if (!fromFab) {
        colorFade.setStartDelay(halfDuration);
        iconFade.setStartDelay(halfDuration);
    }
    colorFade.setDuration(halfDuration);
    iconFade.setDuration(halfDuration);
    colorFade.setInterpolator(fastOutSlowInInterpolator);
    iconFade.setInterpolator(fastOutSlowInInterpolator);

    // Work around issue with elevation shadows. At the end of the return transition the shared
    // element's shadow is drawn twice (by each activity) which is jarring. This workaround
    // still causes the shadow to snap, but it's better than seeing it double drawn.
    Animator elevation = null;
    if (!fromFab) {
        elevation = ObjectAnimator.ofFloat(view, View.TRANSLATION_Z, -view.getElevation());
        elevation.setDuration(duration);
        elevation.setInterpolator(fastOutSlowInInterpolator);
    }

    // Run all animations together
    final AnimatorSet transition = new AnimatorSet();
    transition.playTogether(circularReveal, translate, colorFade, iconFade);
    transition.playTogether(fadeContents);
    if (elevation != null)
        transition.play(elevation);
    if (fromFab) {
        transition.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                // Clean up
                view.getOverlay().clear();
            }
        });
    }
    return new AnimUtils.NoPauseAnimator(transition);
}