58. Local animation loading implementation (Android property animation) and local android

Source: Internet
Author: User

58. Local animation loading implementation (Android property animation) and local android

I recently read the 58-city new version of the app, but I still made a lot of animation effects in it. I saw that loading an animation was quite fun, so I tried it. Let's first look at the effect.

Many people have read this and the first question is how the shadow part is implemented? In fact, if you really want to implement it by yourself, this problem is not a problem, but what is really difficult is how to control the speed of the image to slow down and speed up when it falls, of course, this problem can only be found in the hands-on process.
Here we will follow the steps to implement
1. Implement the layout of the entire LoadingView

Public class LoadingLayout extends RelativeLayout {public LoadingLayout (Context context) {this (context, null);} public LoadingLayout (Context context, AttributeSet attrs) {this (context, attrs, 0);} public LoadingLayout (Context context, AttributeSet attrs, int defStyleAttr) {super (context, attrs, defStyleAttr); // Add the desired part, and arrange initView (getContext () as needed ());}}
Private void initView (Context context) {/* fixed the size of these images to 28 dp values */int viewSize = (int) (28 * getResources (). getDisplayMetrics (). density +. 5f);/* Create a View that displays a circular image */mCircleView = new View (context);/* set the parameter */RelativeLayout. layoutParams circleParams = new LayoutParams (viewSize, viewSize);/* let him horizontally center display */circleParams. addRule (RelativeLayout. CENTER_HORIZONTAL, RelativeLayout. TRUE); mCircleView. setLayoutParams (circleParams);/* set the background image */mCircleView. setBackgroundResource (R. mipmap. loading_yuan);/* sets the id. this parameter is used to arrange the shadow. You need to use this View as the reference object */mCircleView. setId (R. id. action_bar_root);/* Create a View that displays a square image */mRectView = new View (context); RelativeLayout. layoutParams rectParams = new LayoutParams (viewSize, viewSize); rectParams. addRule (RelativeLayout. CENTER_HORIZONTAL, RelativeLayout. TRUE); mRectView. setLayoutParams (rectParams); mRectView. setBackgroundResource (R. mipmap. loading_fangxing);/* Create a View that displays a triangle image */mTriangleView = new View (context); RelativeLayout. layoutParams triangleParams = new LayoutParams (viewSize, viewSize); triangleParams. addRule (RelativeLayout. CENTER_HORIZONTAL, RelativeLayout. TRUE); mTriangleView. setLayoutParams (triangleParams); mTriangleView. setBackgroundResource (R. mipmap. loading_sanjiao);/* Create an ImageView that displays the shadow image at the bottom */mBottomView = new ImageView (context); RelativeLayout. layoutParams bottomParams = new LayoutParams (ViewGroup. layoutParams. WRAP_CONTENT, ViewGroup. layoutParams. WRAP_CONTENT);/* set horizontal center */bottomParams. addRule (RelativeLayout. CENTER_HORIZONTAL, RelativeLayout. TRUE);/* set to the bottom of the circular image */bottomParams. addRule (RelativeLayout. BELOW, R. id. action_bar_root); mBottomView. setLayoutParams (bottomParams); mBottomView. setBackgroundResource (R. mipmap. loading_bottom);/* center View in the entire Layout */setGravity (Gravity. CENTER);/* add View */addView (mCircleView); addView (mRectView); addView (mTriangleView); addView (mBottomView); mRectView. setVisibility (INVISIBLE); mTriangleView. setVisibility (INVISIBLE );}

Here, the first step is complete. We can display the data we want normally. Next, let's take a look at the second step,

2. Set animations for these views to make them all dynamic. Here we will talk about the implementation principle of shadow at the bottom. In fact, there is nothing special, just like the other three pictures, change the scale-down of X through the property animation.

Private void startAnim () {Log. v ("zgy", "========= startAnim ========"); isAnim = true; if (mCircleView. getVisibility ()! = VISIBLE) {mCircleView. setVisibility (VISIBLE); mRectView. setVisibility (INVISIBLE); mTriangleView. setVisibility (INVISIBLE);}/* animated set of circular images */mCircleAnim = new AnimatorSet ();/* set the execution duration of 800 ms */mCircleAnim. setDuration (800L);/* set the number of playback animations, move the animation and hide the shadow at the bottom */mCircleAnim. playTogether (translationAnim (mCircleView), bottomAnim ();/* Start animation */mCircleAnim. start ();/* set the animation listening event */mCircleAnim. addListener (mCircleListener); mRectAnim = new AnimatorSet (); mRectAnim. setStartDelay (800L); mRectAnim. setDuration (800L); mRectAnim. playTogether (translationAnim (mRectView), bottomAnim (), rotationAnim (mRectView); mRectAnim. start (); mRectAnim. addListener (mRectListener); mTriangleAnim = new AnimatorSet (); mTriangleAnim. setStartDelay (1600L); mTriangleAnim. setDuration (800L); mTriangleAnim. playTogether (translationAnim (mTriangleView), bottomAnim (), rotationAnim (mTriangleView); mTriangleAnim. start (); mTriangleAnim. addListener (mTriangleListener );

Now, the animation effect has been achieved. Let's take a look.

However, I always feel that the effect is not correct. Generally, things are falling down, giving people the feeling that the speed of moving down is faster, but here we just make constant changes. Well, let's change the interpolation tool, because the animation is a complete animation from the bottom up and down, its value is:

        mAnimTransValueRec = new float[7];        mAnimTransValueRec[0] = 0f;        mAnimTransValueRec[1] = -50f;        mAnimTransValueRec[2] = -100f;        mAnimTransValueRec[3] = -150f;        mAnimTransValueRec[4] = -100f;        mAnimTransValueRec[5] = -50f;        mAnimTransValueRec[6] = 0f;

So when we set the interpolation tool, we hope to set the interpolation tool that first slows down and then accelerates. However, unfortunately, there are the accelerated interpolation tool and the slow interpolation tool, there is also an interpolation tool that accelerates and then accelerates, that is, it does not provide an interpolation tool that first slows down and accelerates, but it doesn't matter. We can implement it ourselves;
To implement the interpolation

public interface TimeInterpolator {    /**     * Maps a value representing the elapsed fraction of an animation to a value that represents     * the interpolated fraction. This interpolated value is then multiplied by the change in     * value of an animation to derive the animated value at the current elapsed animation time.     *     * @param input A value between 0 and 1.0 indicating our current point     *        in the animation where 0 represents the start and 1.0 represents     *        the end     * @return The interpolation value. This value can be more than 1.0 for     *         interpolators which overshoot their targets, or less than 0 for     *         interpolators that undershoot their targets.     */    float getInterpolation(float input);}

The input value in is converted to another float,

If nothing is done, it is linear change, that is, constant speed change.

/** * An interpolator where the rate of change is constant * */public class LinearInterpolator implements Interpolator {    public LinearInterpolator() {    }    public LinearInterpolator(Context context, AttributeSet attrs) {    }    public float getInterpolation(float input) {        return input;    }}

Let's take a look at the interpolation tool that accelerates and slows down.

/** * An interpolator where the rate of change starts and ends slowly but * accelerates through the middle. *  */public class AccelerateDecelerateInterpolator implements Interpolator {    public AccelerateDecelerateInterpolator() {    }    @SuppressWarnings({"UnusedDeclaration"})    public AccelerateDecelerateInterpolator(Context context, AttributeSet attrs) {    }    public float getInterpolation(float input) {        return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;    }}

Then how can we implement the interpolation tool that first slows down and then accelerates? Based on the above figure, we can know that to achieve the desired effect, it is in the range of 0 ~ The curve between 0.5 and 0.5 should be convex ~ The relationship between 1 and 1 should be concave. The opposite is true. How can this curve be achieved? Let's look at a figure.

The slice is composed of two parabolic results ~ Take parabolic B in the range of 0.5, ranging from 0.5 ~ 1.0 takes parabolic a, which is exactly the curve we want. Based on the mathematical knowledge of High School, the quadratic curve shows that the speed of the curve we take is to slow down and then accelerate.
The following code is used to implement the interpolation tool that first slows down and then accelerates:

public final class DecelerateAccelerateInterpolator implements Interpolator {    public final float getInterpolation(float input) {        if (input < 0.5) {            return - (input * (input/2.0f) -  input/2.0f);        }else {            return 1.0F + (input * (2.0F * input) - 2.0F * input) ;        }    }}

OK. Remember to set the interpolation tool for the animation.

animator.setInterpolator(new DecelerateAccelerateInterpolator());

The final test result is the effect of the first dynamic graph, which is obviously more consistent with the visual logic than the second dynamic graph;

Click Download source code

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.