简体   繁体   中英

Animate a view towards left

I'm using the following code to expand a view with an animation:

public class HorizontallyAnimate extends Animation {

    private int  toWidth;
    private int  startWidth;
    private View view;
    private String TAG = HorizontallyAnimate.class.getSimpleName();
    private int newWidth;
    public HorizontallyAnimate(View view) {
        this.view = view;
        this.startWidth = this.view.getWidth();
        this.toWidth = (this.startWidth == view.getHeight() ? this.startWidth * 4 : view.getHeight());

        Log.d(TAG,"Start width" + this.startWidth);
        Log.d(TAG,"view hieght " + view.getHeight());

    }

    protected void applyTransformation(float interpolatedTime, Transformation t) {
        newWidth = this.startWidth + (int) ((this.toWidth - this.startWidth) * interpolatedTime);
        this.view.getLayoutParams().width = newWidth;
        this.view.requestLayout();
    }

}

The above code animates the view from left to right when the width changes.

But, I'm trying to animate it from the right to left. In other words, the width should grow in opposite direction. How can I be able to do so?

The problem you're dealing with here is an anchoring issue. A view's anchor (or pivot point) determines which point on the view stays still when other parts change.

A view's anchor when adjusting its dimensions highly depends on how the view is laid out. Since you didn't supply any information on how your view is laid out in the code you posted, I'll assume from the problem you're experiencing that the view's horizontal anchor is its left side.

This anchoring issue would produce a growth which would cause the left-most side to stay still, while the right side expands right-wards.

Making the view's left side to expand leftwards while the right side stays still can be achieved in several ways. One way would be to alter the way the view is laid out in its parent (ie, if the parent is a RelativeLayout , set the view to alignParentRight=true , or playing with gravity in other containers).

However, since you didn't specify how the view is laid out, I will give you a solution which does not make any assumptions on its container. This solution isn't perfect as it may cause some stuttering, but it should still achieve what you're trying to do.

In your applyTransformation method, you will need to compensate for the right growth by translating leftwards. You can compensate for this by using translationX :

protected void applyTransformation(float interpolatedTime, Transformation t) {

        // hold the change in a separate variable for reuse.
        int delta = (int) ((this.toWidth - this.startWidth) * interpolatedTime);

        newWidth = this.startWidth + delta;
        this.view.getLayoutParams().width = newWidth;

        // shift the view leftwards so that the right side appears not to move.
        // shift amount should be equal to the amount the view expanded, but in the
        // opposite direction.
        this.view.setTranslationX(-delta); 

        this.view.requestLayout();
    }

As you can see, this is a bit of "trick". While the view is expanding to the right, we are moving it to the left at the exact same ratio which causes the illusion of the view expanding to the left.

Test this code and see if it works for you. I would also recommend seeing if you can play around with the view's alignment or gravity from within its container. Doing this would solve your issue in a more standard manner, ie, without any "tricks".

Hope this helps.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM