CircularReveal动画在首次尝试时不起作用

时间:2015-01-11 15:45:25

标签: android animation android-5.0-lollipop

在android 5.0中,我正在尝试使用圆形显示动画

问题

当我点击按钮开始显示动画时,首次点击动画无法启动

第二次点击它可以正常工作

我的代码

public class MainActivity extends ActionBarActivity {

Animator a;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    final View cardType = findViewById(R.id.cardtype);
    cardType.setVisibility(View.GONE);
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
        a = ViewAnimationUtils.createCircularReveal(cardType,
                cardType.getWidth(),
                cardType.getHeight(),
                0,
                cardType.getHeight() * 2)
                .setDuration(2500);
        a.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationStart(Animator animation) {
                super.onAnimationStart(animation);
                cardType.setVisibility(View.VISIBLE);
            }
        });
        a.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                super.onAnimationEnd(animation);
                cardType.setVisibility(View.GONE);
            }
        });
        findViewById(R.id.icon_first_activity).setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                a.start();
            }
        });
    }
}}

4 个答案:

答案 0 :(得分:30)

我还没有尝试过您的代码,但我认为您的订购问题很少。我认为您只需要在开始动画之前设置cardType可见

已编辑添加:

...你应该设置按钮View.INVISIBLE,而不是View.GONE。

此处:This code works

再次编辑添加:

是。您的问题是您最初设置了GONE视图。这意味着它有0个大小。然后使用cardType.getHeightcardType.getWidth作为显示坐标。它们是0.您最初要将视图设置为INVISIBLE,然后使用width / 2和height / 2作为显示的中心。

答案 1 :(得分:6)

基本上其他人的回答说,这是正确的,但问题是如果你想要可见性GONE(因为你的布局要求GONE!)你必须在高度为0dp的xml中设置可见性INVISIBLE(和/或width 0dp)并以编程方式设置正确的LayoutParams甚至在它将起作用的click事件中。例如我的代码:

    ...
    expandButton.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            //To not have empty scroll, the container is INVISIBLE with 0dp height.
            //Otherwise the Reveal effect will not work at the first click.
            //Here I set the parameters programmatically.
            viewContainer.setLayoutParams(new LinearLayout.LayoutParams(
                    ViewGroup.LayoutParams.MATCH_PARENT,
                    ViewGroup.LayoutParams.WRAP_CONTENT));

            if (viewContainer.getVisibility() == View.VISIBLE) {
                expandButton.animate().rotation(0f).setDuration(duration).start();
                Utils.unReveal(viewContainer, 0, 0);
            } else {
                expandButton.animate().rotation(180f).setDuration(duration).start();
                Utils.reveal(viewContainer, viewContainer.getWidth(), 0);
            }
        }
    });
    ...

@TargetApi(VERSION_CODES.LOLLIPOP)
public static void reveal(final View view, int cx, int cy) {
    if (!hasLollipop()) {
        view.setVisibility(View.VISIBLE);
        return;
    }

    //Get the final radius for the clipping circle
    int finalRadius = Math.max(view.getWidth(), view.getHeight());

    //Create the animator for this view (the start radius is zero)
    Animator animator =
            ViewAnimationUtils.createCircularReveal(view, cx, cy, 0, finalRadius);

    //Make the view VISIBLE and start the animation
    view.setVisibility(View.VISIBLE);
    animator.start();
}

@TargetApi(VERSION_CODES.LOLLIPOP)
public static void unReveal(final View view, int cx, int cy) {
    if (!hasLollipop()) {
        view.setVisibility(View.GONE);
        return;
    }

    //Get the initial radius for the clipping circle
    int initialRadius = view.getWidth();

    //Create the animation (the final radius is zero)
    Animator animator =
        ViewAnimationUtils.createCircularReveal(view, cx, cy, initialRadius, 0);

    //Make the view GONE when the animation is done
    animator.addListener(new AnimatorListenerAdapter() {
        @Override
        public void onAnimationEnd(Animator animation) {
            super.onAnimationEnd(animation);
            view.setVisibility(View.GONE);
        }
    });

    //Start the animation
    animator.start();
}

如果你只在xml中设置GONE,第一次将永远不会工作,因为height / width / x / y / etc ..是0.另外,如果你只是在调用动画之前设置了INVISIBLE它将也可以工作,但如果从可见性开始可见,它将初始化布局参数。

答案 2 :(得分:0)

我所做的是,就像我有两个相同高度的视图一样,因为我们现在的可见度变为0 {高度和宽度},而不是每次都给出可见的视图高度,而且它对我有效。

答案 3 :(得分:-1)

解决方案是不直接将值获取到代码中 要么点击动画代码,要么点击外面的值 或从其他活动中获取值


我认为值cardType.getWidth()cardType.getHeight()