本文介绍了Android圆形揭露动画的使用。
原文链接:Circular Reveal Animation
概述
揭露动画是Android L中新引入的动画,裁剪View的边界的动画。当显示或隐藏一组UI元素时揭露动画可以给用户提供视觉连续性。这个动画经常用在悬浮按钮上。
配置
使用ViewAnimationUtils.createCircularReveal()
方法可以创建揭露动画。
对于未显示的View使用下面的代码产生揭露动画:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19void enterReveal() {
// previously invisible view
final View myView = findViewById(R.id.my_view);
// get the center for the clipping circle
int cx = myView.getMeasuredWidth() / 2;
int cy = myView.getMeasuredHeight() / 2;
// get the final radius for the clipping circle
int finalRadius = Math.max(myView.getWidth(), myView.getHeight()) / 2;
// create the animator for this view (the start radius is zero)
Animator anim =
ViewAnimationUtils.createCircularReveal(myView, cx, cy, 0, finalRadius);
// make the view visible and start the animation
myView.setVisibility(View.VISIBLE);
anim.start();
}
隐藏已显示的View使用下面的代码:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27void exitReveal() {
// previously visible view
final View myView = findViewById(R.id.my_view);
// get the center for the clipping circle
int cx = myView.getMeasuredWidth() / 2;
int cy = myView.getMeasuredHeight() / 2;
// get the initial radius for the clipping circle
int initialRadius = myView.getWidth() / 2;
// create the animation (the final radius is zero)
Animator anim =
ViewAnimationUtils.createCircularReveal(myView, cx, cy, initialRadius, 0);
// make the view invisible when the animation is done
anim.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
super.onAnimationEnd(animation);
myView.setVisibility(View.INVISIBLE);
}
});
// start the animation
anim.start();
}
View过渡
在Activity进入过渡完成之后调用enterReveal()
:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35private Transition.TransitionListener mEnterTransitionListener;
@Override
protected void onCreate(Bundle savedInstanceState) {
...
mEnterTransitionListener = new Transition.TransitionListener() {
@Override
public void onTransitionStart(Transition transition) {
}
@Override
public void onTransitionEnd(Transition transition) {
enterReveal();
}
@Override
public void onTransitionCancel(Transition transition) {
}
@Override
public void onTransitionPause(Transition transition) {
}
@Override
public void onTransitionResume(Transition transition) {
}
};
getWindow().getEnterTransition().addListener(mEnterTransitionListener);
}
修改enterReveal()
方法当动画结束后移除监听。
1 | private void enterReveal() { |
退出揭露动画完成之后销毁Activity:1
2
3
4
5
6
7
8
9
10anim.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
super.onAnimationEnd(animation);
myView.setVisibility(View.INVISIBLE);
// Finish the activity after the exit transition completes.
supportFinishAfterTransition();
}
});
为了开启ActionBar的向上或返回按钮的退出揭露过渡,分别在onOptionsItemSelected()和onBackPressed()调用exitReveal()。1
2
3
4
5
6
7
8
9
10
11
12
13
14
15@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
// Respond to the action bar's Up/Home button
case android.R.id.home:
exitReveal();
return true;
}
return super.onOptionsItemSelected(item);
}
@Override
public void onBackPressed() {
exitReveal();
}
常见问题
如果你直接在View上使用揭露动画,它可能看起来有些奇怪,因此图形的一部分边也被揭露了。为了解决这个问题,你可以把View嵌入到用描边作为背景的FrameLayout中。通过这样处理,揭露动画的View和背景部分保持一致,因此它看起来只有颜色部分被揭露。
circular_button.xml:
1 | <?xml version="1.0" encoding="utf-8"?> |
1 | <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" |
高级
为了当用户轻击View让揭露动画开始时看起来更自然,你可以从MotionEvent获取x和y的坐标,使用它开启揭露效果。
1 | @Override |
参考
- https://developer.android.com/training/material/animations.html
- http://trickyandroid.com/simple-ripple-reveal-elevation-tutorial/