4.4.2 Android属性动画完全解析(下) Interpolator和ViewPropertyAnimator的用法

Android 常见 插值器 (Interpolator) 文章目录1、简介2、插值器的引用1) 在 xml 里面引用2) 在代码里引用3、AccelerateDecelerateInterpolator 加速减速插值器3、AccelerateInterpolator 加速插值器 1、简介 Interpolator 叫插值器,也叫做加速器,用来指定动画如何变化的量。 系统常见的插值器有如下几种: 2、插值器的引用 1) 在 xml 里面引用 通过an... 阅读详情

Android属性动画完全解析(下) Interpolator和ViewPropertyAnimator的用法

作者:  发布日期:2015-06-04 20:20:06
Tag标签: 属性   动画  
  •  http://www.it165.net/pro/html/201506/42870.html

    大家好,欢迎继续回到Android属性动画完全解析。在上一篇文章当中我们学习了属性动画的一些进阶技巧,包括ValueAnimator和ObjectAnimator的高级用法,那么除了这些之外,当然还有一些其它的高级技巧在等着我们学习,因此本篇文章就对整个属性动画完全解析系列收个尾,来学习一下剩下的非常重要的高级技巧。

    另外,本篇文章中使用的代码是建立在上篇文章基础之上的,如果你还没有阅读过前面的文章,建议先去参考阅读一下 Android属性动画完全解析(中),ValueAnimator和ObjectAnimator的高级用法 。

    Interpolator的用法

    Interpolator这个东西很难进行翻译,直译过来的话是补间器的意思,它的主要作用是可以控制动画的变化速率,比如去实现一种非线性运动的动画效果。那么什么叫做非线性运动的动画效果呢?就是说动画改变的速率不是一成不变的,像加速运动以及减速运动都属于非线性运动。

    不过Interpolator并不是属性动画中新增的技术,实际上从Android 1.0版本开始就一直存在Interpolator接口了,而之前的补间动画当然也是支持这个功能的。只不过在属性动画中新增了一个TimeInterpolator接口,这个接口是用于兼容之前的Interpolator的,这使得所有过去的Interpolator实现类都可以直接拿过来放到属性动画当中使用,那么我们来看一下现在TimeInterpolator接口的所有实现类,如下图所示:

    可以看到,TimeInterpolator接口已经有非常多的实现类了,这些都是Android系统内置好的并且我们可以直接使用的Interpolator。每个Interpolator都有它各自的实现效果,比如说AccelerateInterpolator就是一个加速运动的Interpolator,而DecelerateInterpolator就是一个减速运动的Interpolator。

    我觉得细心的朋友应该早已经发现了,在前面两篇文章当中我们所学到的所有属性动画,其实都不是在进行一种线程运动。比如说在“上”篇文章中使用ValueAnimator所打印的值如下所示:

    可以看到,一开始的值变化速度明显比较慢,仅0.0开头的就打印了4次,之后开始加速,最后阶段又开始减速,因此我们可以很明显地看出这一个先加速后减速的Interpolator。

    那么再来看一下在“中”篇文章中完成的小球移动加变色的功能,如下图所示:

    从上图中我们明显可以看出,小球一开始运动速度比较慢,然后逐渐加速,中间的部分运动速度就比较快,接下来开始减速,最后缓缓停住。另外颜色变化也是这种规律,一开始颜色变化的比较慢,中间颜色变化的很快,最后阶段颜色变化的又比较慢。

    从以上几点我们就可以总结出一个结论了,使用属性动画时,系统默认的Interpolator其实就是一个先加速后减速的Interpolator,对应的实现类就是AccelerateDecelerateInterpolator。

    当然,我们也可以很轻松地修改这一默认属性,将它替换成任意一个系统内置好的Interpolator。就拿“中”篇文章中的代码来举例吧,MyAnimView中的startAnimation()方法是开启动画效果的入口,这里我们对Point对象的坐标稍做一下修改,让它变成一种垂直掉落的效果,代码如下所示:

    01. private void startAnimation() {
    02. Point startPoint = new Point(getWidth() / 2, RADIUS);
    03. Point endPoint = new Point(getWidth() / 2, getHeight() - RADIUS);
    04. ValueAnimator anim = ValueAnimator.ofObject(new PointEvaluator(), startPoint, endPoint);
    05. anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
    06. @Override
    07. public void onAnimationUpdate(ValueAnimator animation) {
    08. currentPoint = (Point) animation.getAnimatedValue();
    09. invalidate();
    10. }
    11. });
    12. anim.setDuration(2000);
    13. anim.start();
    14. }
    这里主要是对Point构造函数中的坐标值进行了一下改动,那么现在小球运动的动画效果应该是从屏幕正中央的顶部掉落到底部。但是现在默认情况下小球的下降速度肯定是先加速后减速的,这不符合物理的常识规律,如果把小球视为一个自由落体的话,那么下降的速度应该是越来越快的。我们怎样才能改变这一默认行为呢?其实很简单,调用Animator的setInterpolator()方法就可以了,这个方法要求传入一个实现TimeInterpolator接口的实例,那么比如说我们想要实现小球下降越来越快的效果,就可以使用AccelerateInterpolator,代码如下所示:
    01. private void startAnimation() {
    02. Point startPoint = new Point(getWidth() / 2, RADIUS);
    03. Point endPoint = new Point(getWidth() / 2, getHeight() - RADIUS);
    04. ValueAnimator anim = ValueAnimator.ofObject(new PointEvaluator(), startPoint, endPoint);
    05. anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
    06. @Override
    07. public void onAnimationUpdate(ValueAnimator animation) {
    08. currentPoint = (Point) animation.getAnimatedValue();
    09. invalidate();
    10. }
    11. });
    12. anim.setInterpolator(new AccelerateInterpolator(2f));
    13. anim.setDuration(2500);
    14. anim.start();
    15. }

    代码很简单,这里调用了setInterpolator()方法,然后传入了一个AccelerateInterpolator的实例,注意AccelerateInterpolator的构建函数可以接收一个float类型的参数,这个参数是用于控制加速度的。现在运行一下代码,效果如下图所示:

    OK,效果非常明显,说明我们已经成功替换掉了默认的Interpolator,AccelerateInterpolator确实是生效了。但是现在的动画效果看上去仍然是怪怪的,因为一个小球从很高的地方掉落到地面上直接就静止了,这也是不符合物理规律的,小球撞击到地面之后应该要反弹起来,然后再次落下,接着再反弹起来,又再次落下,以此反复,最后静止。这个功能我们当然可以自己去写,只不过比较复杂,所幸的是,Android系统中已经提供好了这样一种Interpolator,我们只需要简单地替换一下就可以完成上面的描述的效果,代码如下所示:

    01. private void startAnimation() {
    02. Point startPoint = new Point(getWidth() / 2, RADIUS);
    03. Point endPoint = new Point(getWidth() / 2, getHeight() - RADIUS);
    04. ValueAnimator anim = ValueAnimator.ofObject(new PointEvaluator(), startPoint, endPoint);
    05. anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
    06. @Override
    07. public void onAnimationUpdate(ValueAnimator animation) {
    08. currentPoint = (Point) animation.getAnimatedValue();
    09. invalidate();
    10. }
    11. });
    12. anim.setInterpolator(new BounceInterpolator());
    13. anim.setDuration(3000);
    14. anim.start();
    15. }
    可以看到,我们只是将设置的Interpolator换成了BounceInterpolator的实例,而BounceInterpolator就是一种可以模拟物理规律,实现反复弹起效果的Interpolator。另外还将整体的动画时间稍微延长了一点,因为小球反复弹起需要比之前更长的时间。现在重新运行一下代码,效果如下图所示:

    OK!效果还是非常不错的。那么这里我们只是选了几个系统实现好的Interpolator,由于内置Interpolator非常多,就不一一进行讲解了,大家可以自己去使用一下其它的几种Interpolator来看一看效果。

    但是,只会用一下系统提供好的Interpolator,我们显然对自己的要求就太低了,既然是学习属性动画的高级用法,那么自然要将它研究透了。下面我们就来看一下Interpolator的内部实现机制是什么样的,并且来尝试写一个自定义的Interpolator。

    首先看一下TimeInterpolator的接口定义,代码如下所示:

    01. /**
    02. * A time interpolator defines the rate of change of an animation. This allows animations
    03. * to have non-linear motion, such as acceleration and deceleration.
    04. */
    05. public interface TimeInterpolator {
    06.  
    07. /**
    08. * Maps a value representing the elapsed fraction of an animation to a value that represents
    09. * the interpolated fraction. This interpolated value is then multiplied by the change in
    10. * value of an animation to derive the animated value at the current elapsed animation time.
    11. *
    12. * @param input A value between 0 and 1.0 indicating our current point
    13. *        in the animation where 0 represents the start and 1.0 represents
    14. *        the end
    15. * @return The interpolation value. This value can be more than 1.0 for
    16. *         interpolators which overshoot their targets, or less than 0 for
    17. *         interpolators that undershoot their targets.
    18. */
    19. float getInterpolation(float input);
    20. }

    OK,接口还是非常简单的,只有一个getInterpolation()方法。大家有兴趣可以通过注释来对这个接口进行详解的了解,这里我就简单解释一下,getInterpolation()方法中接收一个input参数,这个参数的值会随着动画的运行而不断变化,不过它的变化是非常有规律的,就是根据设定的动画时长匀速增加,变化范围是0到1。也就是说当动画一开始的时候input的值是0,到动画结束的时候input的值是1,而中间的值则是随着动画运行的时长在0到1之间变化的。

    说到这个input的值,我觉得有不少朋友可能会联想到我们在“中”篇文章中使用过的fraction值。那么这里的input和fraction有什么关系或者区别呢?答案很简单,input的值决定了fraction的值。input的值是由系统经过计算后传入到getInterpolation()方法中的,然后我们可以自己实现getInterpolation()方法中的算法,根据input的值来计算出一个返回值,而这个返回值就是fraction了。

    因此,最简单的情况就是input值和fraction值是相同的,这种情况由于input值是匀速增加的,因而fraction的值也是匀速增加的,所以动画的运动情况也是匀速的。系统中内置的LinearInterpolator就是一种匀速运动的Interpolator,那么我们来看一下它的源码是怎么实现的:

    01. /**
    02. * An interpolator where the rate of change is constant
    03. */
    04. @HasNativeInterpolator
    05. public class LinearInterpolator extends BaseInterpolator implements NativeInterpolatorFactory {
    06.  
    07. public LinearInterpolator() {
    08. }
    09.  
    10. public LinearInterpolator(Context context, AttributeSet attrs) {
    11. }
    12.  
    13. public float getInterpolation(float input) {
    14. return input;
    15. }
    16.  
    17. /** @hide */
    18. @Override
    19. public long createNativeInterpolator() {
    20. return NativeInterpolatorFactoryHelper.createLinearInterpolator();
    21. }
    22. }

    这里我们只看getInterpolation()方法,这个方法没有任何逻辑,就是把参数中传递的input值直接返回了,因此fraction的值就是等于input的值的,这就是匀速运动的Interpolator的实现方式。

    当然这是最简单的一种Interpolator的实现了,我们再来看一个稍微复杂一点的。既然现在大家都知道了系统在默认情况下使用的是AccelerateDecelerateInterpolator,那我们就来看一下它的源码吧,如下所示:

    01. /**
    02. * An interpolator where the rate of change starts and ends slowly but
    03. * accelerates through the middle.
    04. *
    05. */
    06. @HasNativeInterpolator
    07. public class AccelerateDecelerateInterpolator implements Interpolator, NativeInterpolatorFactory {
    08. public AccelerateDecelerateInterpolator() {
    09. }
    10.  
    11. @SuppressWarnings({"UnusedDeclaration"})
    12. public AccelerateDecelerateInterpolator(Context context, AttributeSet attrs) {
    13. }
    14.  
    15. public float getInterpolation(float input) {
    16. return (float)(Math.cos((input + 1) * Math.PI) / 2.0f) + 0.5f;
    17. }
    18.  
    19. /** @hide */
    20. @Override
    21. public long createNativeInterpolator() {
    22. return NativeInterpolatorFactoryHelper.createAccelerateDecelerateInterpolator();
    23. }
    24. }
    代码虽然没有变长很多,但是getInterpolation()方法中的逻辑已经明显变复杂了,不再是简单地将参数中的input进行返回,而是进行了一个较为复杂的数学运算。那这里我们来分析一下它的算法实现,可以看到,算法中主要使用了余弦函数,由于input的取值范围是0到1,那么cos函数中的取值范围就是π到2π。而cos(π)的结果是-1,cos(2π)的结果是1,那么这个值再除以2加上0.5之后,getInterpolation()方法最终返回的结果值还是在0到1之间。只不过经过了余弦运算之后,最终的结果不再是匀速增加的了,而是经历了一个先加速后减速的过程。我们可以将这个算法的执行情况通过曲线图的方式绘制出来,结果如下图所示:

    可以看到,这是一个S型的曲线图,当横坐标从0变化到0.2的时候,纵坐标的变化幅度很小,但是之后就开始明显加速,最后横坐标从0.8变化到1的时候,纵坐标的变化幅度又变得很小。

    OK,通过分析LinearInterpolator和AccelerateDecelerateInterpolator的源码,我们已经对Interpolator的内部实现机制有了比较清楚的认识了,那么接下来我们就开始尝试编写一个自定义的Interpolator。

    编写自定义Interpolator最主要的难度都是在于数学计算方面的,由于我数学并不是很好,因此这里也就写一个简单点的Interpolator来给大家演示一下。既然属性动画默认的Interpolator是先加速后减速的一种方式,这里我们就对它进行一个简单的修改,让它变成先减速后加速的方式。新建DecelerateAccelerateInterpolator类,让它实现TimeInterpolator接口,代码如下所示:

    01. public class DecelerateAccelerateInterpolator implements TimeInterpolator{
    02.  
    03. @Override
    04. public float getInterpolation(float input) {
    05. float result;
    06. if (input <= 0.5) {
    07. result = (float) (Math.sin(Math.PI * input)) / 2;
    08. } else {
    09. result = (float) (2 - Math.sin(Math.PI * input)) / 2;
    10. }
    11. return result;
    12. }
    13.  
    14. }
    这段代码是使用正弦函数来实现先减速后加速的功能的,因为正弦函数初始弧度的变化值非常大,刚好和余弦函数是相反的,而随着弧度的增加,正弦函数的变化值也会逐渐变小,这样也就实现了减速的效果。当弧度大于π/2之后,整个过程相反了过来,现在正弦函数的弧度变化值非常小,渐渐随着弧度继续增加,变化值越来越大,弧度到π时结束,这样从0过度到π,也就实现了先减速后加速的效果。

    同样我们可以将这个算法的执行情况通过曲线图的方式绘制出来,结果如下图所示:

    可以看到,这也是一个S型的曲线图,只不过曲线的方向和刚才是相反的。从上图中我们可以很清楚地看出来,一开始纵坐标的变化幅度很大,然后逐渐变小,横坐标到0.5的时候纵坐标变化幅度趋近于零,之后随着横坐标继续增加纵坐标的变化幅度又开始变大,的确是先减速后加速的效果。

    那么现在我们将DecelerateAccelerateInterpolator在代码中进行替换,如下所示:

    01. private void startAnimation() {
    02. Point startPoint = new Point(getWidth() / 2, RADIUS);
    03. Point endPoint = new Point(getWidth() / 2, getHeight() - RADIUS);
    04. ValueAnimator anim = ValueAnimator.ofObject(new PointEvaluator(), startPoint, endPoint);
    05. anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
    06. @Override
    07. public void onAnimationUpdate(ValueAnimator animation) {
    08. currentPoint = (Point) animation.getAnimatedValue();
    09. invalidate();
    10. }
    11. });
    12. anim.setInterpolator(new DecelerateAccelerateInterpolator());
    13. anim.setDuration(3000);
    14. anim.start();
    15. }

    非常简单,就是将DecelerateAccelerateInterpolator的实例传入到setInterpolator()方法当中。重新运行一下代码,效果如下图所示:

    OK!小球的运动确实是先减速后加速的效果,说明我们自定义的Interpolator已经可以正常工作了。通过这样一个程度的学习,相信大家对属性动画Interpolator的理解和使用都达到了一个比较深刻的层次了。

    ViewPropertyAnimator的用法

    ViewPropertyAnimator其实算不上什么高级技巧,它的用法格外的简单,只不过和前面所学的所有属性动画的知识不同,它并不是在3.0系统当中引入的,而是在3.1系统当中附增的一个新的功能,因此这里我们把它作为整个属性动画系列的收尾部分。

    我们都知道,属性动画的机制已经不是再针对于View而进行设计的了,而是一种不断地对值进行操作的机制,它可以将值赋值到指定对象的指定属性上。但是,在绝大多数情况下,我相信大家主要都还是对View进行动画操作的。Android开发团队也是意识到了这一点,没有为View的动画操作提供一种更加便捷的用法确实是有点太不人性化了,于是在Android 3.1系统当中补充了ViewPropertyAnimator这个机制。

    那我们先来回顾一下之前的用法吧,比如我们想要让一个TextView从常规状态变成透明状态,就可以这样写:

    1. ObjectAnimator animator = ObjectAnimator.ofFloat(textview, "alpha", 0f);
    2. animator.start();
    看上去复杂吗?好像也不怎么复杂,但确实也不怎么容易理解。我们要将操作的view、属性、变化的值都一起传入到ObjectAnimator.ofFloat()方法当中,虽然看上去也没写几行代码,但这不太像是我们平时使用的面向对象的思维。

     

    那么下面我们就来看一下如何使用ViewPropertyAnimator来实现同样的效果,ViewPropertyAnimator提供了更加易懂、更加面向对象的API,如下所示:

    1. textview.animate().alpha(0f);

    果然非常简单!不过textview.animate()这个方法是怎么回事呢?animate()方法就是在Android 3.1系统上新增的一个方法,这个方法的返回值是一个ViewPropertyAnimator对象,也就是说拿到这个对象之后我们就可以调用它的各种方法来实现动画效果了,这里我们调用了alpha()方法并转入0,表示将当前的textview变成透明状态。

    怎么样?比起使用ObjectAnimator,ViewPropertyAnimator的用法明显更加简单易懂吧。除此之外,ViewPropertyAnimator还可以很轻松地将多个动画组合到一起,比如我们想要让textview运动到500,500这个坐标点上,就可以这样写:

    1. textview.animate().x(500).y(500);
    可以看出,ViewPropertyAnimator是支持连缀用法的,我们想让textview移动到横坐标500这个位置上时调用了x(500)这个方法,然后让textview移动到纵坐标500这个位置上时调用了y(500)这个方法,将所有想要组合的动画通过这种连缀的方式拼接起来,这样全部动画就都会一起被执行。

     

    那么怎样去设定动画的运行时长呢?很简单,也是通过连缀的方式设定即可,比如我们想要让动画运行5秒钟,就可以这样写:

    1. textview.animate().x(500).y(500).setDuration(5000);
    除此之外,本篇文章第一部分所学的Interpolator技术我们也可以应用在ViewPropertyAnimator上面,如下所示:
    1. textview.animate().x(500).y(500).setDuration(5000)
    2. .setInterpolator(new BounceInterpolator());
    用法很简单,同样也是使用连缀的方式。相信大家现在都已经体验出来了,ViewPropertyAnimator其实并没有什么太多的技巧可言,用法基本都是大同小异的,需要用到什么功能就连缀一下,因此更多的用法大家只需要去查阅一下文档,看看还支持哪些功能,有哪些接口可以调用就可以了。

     

    那么除了用法之外,关于ViewPropertyAnimator有几个细节还是值得大家注意一下的:

    整个ViewPropertyAnimator的功能都是建立在View类新增的animate()方法之上的,这个方法会创建并返回一个ViewPropertyAnimator的实例,之后的调用的所有方法,设置的所有属性都是通过这个实例完成的。大家注意到,在使用ViewPropertyAnimator时,我们自始至终没有调用过start()方法,这是因为新的接口中使用了隐式启动动画的功能,只要我们将动画定义完成之后,动画就会自动启动。并且这个机制对于组合动画也同样有效,只要我们不断地连缀新的方法,那么动画就不会立刻执行,等到所有在ViewPropertyAnimator上设置的方法都执行完毕后,动画就会自动启动。当然如果不想使用这一默认机制的话,我们也可以显式地调用start()方法来启动动画。ViewPropertyAnimator的所有接口都是使用连缀的语法来设计的,每个方法的返回值都是它自身的实例,因此调用完一个方法之后可以直接连缀调用它的另一个方法,这样把所有的功能都串接起来,我们甚至可以仅通过一行代码就完成任意复杂度的动画功能。

    好的,那么到这里为止,整个Android属性动画完全解析的系列就全部结束了,感谢大家有耐心看到最后。

    出处:http://blog.youkuaiyun.com/guolin_blog/article/details/44171115

Android动画介绍——插值器 此时动画时间被转换为时间索引,则动画时间轴上的每个点都可以转换成0.0到1.0之间的一个浮点数。在变换的情况下,y轴上,0.0对应于起始位置,1.0对应于结束位置,0.5对应于起始和结束之间的中间,对于一些插值器其值还可以是0~1之外的数值。通俗易懂的说,Interpolator负责控制动画变化的速率,即确定了 动画效果变化的模式,使得基本的动画效果能够以匀速、加速、减速、抛物线速率等各种速率变化。跳跃,快到目的值时值会跳跃,如目的值100,后面的值可能依次为85,77,70,80,90,100。 阅读详情

相关推荐

Cadence ADE实战:1GHz VCO相位噪声仿真全流程(附PSS/Pnoise避坑指南)

本文详细介绍了在Cadence ADE环境中对1GHz VCO进行相位噪声仿真的完整流程。重点剖析了PSS(周期性稳态分析)和Pnoise(周期性噪声分析)两大核心引擎的关键参数设置与避坑指南,帮助射频与模拟IC设计者准确评估VCO性能,解决仿真不收敛、结果异常等常见问题。

rock5的博客 669

安卓属性动画插值器(Interpolator)详解

插值器(Interpolator)是用来控制动画执行速率的工具。在安卓的动画框架中,插值器主要用于指定动画从开始到结束的时间进度曲线。简单来说,插值器控制了动画的“快慢”,即时间与进度之间的关系。安卓提供了一系列内置的插值器,可以帮助开发者更好地控制动画的节奏,开发者也可以通过自定义插值器来实现更独特的效果。

WriteBug001的博客 2712

【ISP图像处理】Demosaic去马赛克技术演进与边缘优化策略

本文深入解析了ISP图像处理中的Demosaic(去马赛克)技术。从Bayer阵列原理出发,梳理了从双线性插值、Hamilton-Adams边缘导向算法到利用通道相关性与自相似性的技术演进历程,并重点探讨了针对边缘与纹理伪影的优化策略,为工程实践中的算法选型与硬件协同设计提供了专业指导。

weixin_29091445的博客 387

Android:插值器(Interpolator)和估值器(TypeEvaluator)的理解和使用

插值器(Interpolator)和估值器(TypeEvaluator)插值器和估值器的理解和使用1、前言2、插值器简介2.1、定义2.2、分类2.2.1、Linear Interpolator 线性插值2.2.2、Accelerate Interpolator / 加速度插值器2.2.3、Decelerate Interpolator / 减速插值器2.2.4 、Accelerate Decelerate Interpolator / 先加速后减速插值器2.2.5、Anticipate Interpola

JMW1407的博客 5451

dify案例-基于Dify打造智能合同审查助手:零代码搭建工作流全指南

Dify的工作流(Workflow)功能是一个可视化流程编排工具,允许用户通过拖拽节点的方式构建复杂的AI应用。与简单的问答应用不同,工作流支持多步骤任务处理、条件分支、并行执行等高级功能,非常适合合同审查这类结构化任务。可视化编排:无需编写代码,通过拖拽连接节点即可构建复杂流程多模型协作:可在不同节点使用最适合的AI模型灵活集成:支持知识库检索、条件判断、API调用等多种节点类型迭代优化:可随时测试和调整单个节点,不影响整体流程可视化搭建:无需编码经验,拖拽式构建复杂审查流程灵活扩展。

weixin_44245188的博客 1939

linux cma alloc fail 问题分析

摘要:日志显示CMA连续内存分配失败(错误码-ENOMEM),请求128页(512KB)内存时因CMA区域不足或内存碎片导致失败。分析发现系统CMA总内存131072KB,空闲65536KB。解决方案包括:1)手动触发内存碎片整理;2)修改设备树或内核配置增大CMA区域(如从16MB增至20MB)。通过调整CONFIG_CMA_SIZE_MBYTES或设备树中的size参数可解决该问题。

陌上花开缓缓归以的博客 797

android 动画中插值器Interpolator详解

android 插值器

muranfei的博客 3902

100天精通Python(可视化篇)——第89天:Bokeh库绘图可视化基础入门(参数说明+案例实战)

专栏导读 一、Bokeh是什么? 二、安装与导入 三、Bokeh接口介绍 四、创建图表 五、添加自定义渲染器 切换主题 添加图例 图例位置 图例方向 图例背景和边界 图例文本的外观 行列布局 网格布局

努力让自己发光,对的人才能迎着光而来 1万+

Android属性动画完全解析(下),Interpolator和ViewPropertyAnimator的用法

大家好,欢迎继续回到Android属性动画完全解析。在上一篇文章当中我们学习了属性动画的一些进阶技巧,包括ValueAnimator和ObjectAnimator的高级用法,那么除了这些之外,当然还有一些其它的高级技巧在等着我们学习,因此本篇文章就对整个属性动画完全解析系列收个尾,来学习一下剩下的非常重要的高级技巧。nterpolator这个东西很难进行翻译,直译过来的话是补间器的意思,它的主要作用是可以控制动画的变化速率,比如去实现一种非线性运动的动画效果。那么什么叫做非线性运动的动画效果呢?就是说动画改

郭霖的专栏 9万+

【云原生进阶之容器】第六章容器网络6.6.2--Cilium部署

部署Cilium非常简单,可以通过单独的yaml文件部署全部组件(目前我使用了这个方式部署了1.7.1版本),也可以通过Helm Chart一键完成。重要的是部署环境和时机:官方建议所有部署节点都使用Linux最新稳定内核版本,这样所有的功能都能启用。作为一个Kubernetes网络组件,它应该在部署Kubernetes其他基础组件之后,才进行部署。

junbaozi的专栏 792

AI使能的SVD算子:基于深度学习的矩阵分解方法

奇异值分解(Singular Value Decomposition, SVD)是线性代数中一种重要的矩阵分解方法,广泛应用于信号处理、数据降维、推荐系统等领域。传统SVD算法虽然精确,但在处理大规模矩阵时面临计算复杂度高、内存需求大等问题。本文提出了一种基于深度学习神经网络的SVD算子实现方法,完全摒弃传统数值算法,仅使用PyTorch框架构建的神经网络模型来完成大规模信道矩阵的SVD分解与还原。

huanghm88的专栏 1322

Android属性动画(下),InterPolator、ViewPropertyAnimator和布局动画的用法

前言:又一个礼拜过去了,原本定下的目标又被落在了脑后,但是懊悔已没什么用,收收心,再向目标前进吧! 等目标被一个一个实现的时候,那才是真正收获的时刻,加油!!时间过去了这么久了,都忘了前两篇博客中都讲了什么了,现在我们先来回顾一下:我们在Android属性动画详解(上),初始属性动画的基本用法中讲解了属性动画的几种常见的操作(淡入淡出、缩放、平移、旋转等),在 Android属性动画解析(中),Va

RookieLog的博客 1235

RK3588部署YOLOv11与RKNN全流程教程

本文详细介绍了在RK3588开发板上部署YOLOv11目标检测模型的全流程。主要内容包括:PC端CUDA/cuDNN环境配置、Anaconda虚拟环境搭建、RKNN Toolkit2安装;YOLOv11模型从PyTorch到ONNX再到RKNN的格式转换;以及RK3588开发板的系统配置、RKNPU驱动安装和最终推理实现。教程提供了完整的代码示例,帮助开发者快速在边缘设备上实现高效的AI推理应用,涵盖从环境准备到实时检测的全套解决方案。

FJN110的博客 375

Android属性动画完全解析 下 ,Interpolator和ViewPropertyAnimator的用法

Android属性动画完全解析 下 ,Interpolator和ViewPropertyAnimator的用法

hfdhjjj的博客 214

IEM模型,地表粗糙度模拟

利用微波反演土壤水分时候,利用IEM模型可以实现对随机地表的模拟

lwip-2.0.3

lwip是瑞典计算机科学院(SICS)的Adam Dunkels 开发的一个小型开源的TCP/IP协议栈。实现的重点是在保持TCP协议主要功能的基础上减少对RAM 的占用。

Android Interpolator属性动画解析

Interpolator的用法Interpolator这个东西很难进行翻译,直译过来的话是补间器的意思,它的主要作用是可以控制动画的变化速率,比如去实现一种非线性运动的动画效果。那么什么叫做非线性运动的动画效果呢?就是说动画改变的速率不是一成不变的,像加速运动以及减速运动都属于非线性运动。不过Interpolator并不是属性动画中新增的技术,实际上从Android 1.0版本开始就一直存在Inte

成长的味道 1165

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

Android动画深入分析-属性动画插值器Interpolator 和ViewPropertyAnimator使用

我们会见到动画播放由快到慢播放、匀速播放、先加速后减速播放。这些效果都是通过插值器来实现的。 Interpolator 简介 1、作用 可以控制动画的变化速率 2、须知 1、Interpolator并不是属性动画中新增的技术,实际上从Android 1.0版本开始就一直存在Interpolator接口 2、补间动画也是支持这个功能的 3、属性动画中新增了一个TimeInterpolato...

dev晴天的博客 338

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

三谈属性动画——Keyframe以及ViewPropertyAnimator

经过初识属性动画——使用Animator创建动画和再谈属性动画——介绍以及自定义Interpolator插值器,对属性动画已经介绍的差不多了,还剩下最后两个概念,Keyframe和ViewPropertyAnimator。 Keyframe 动画归根结底是一些帧的组合,一旦设定了一个动画后,中间的每帧,Android系统会帮我们计算好,而Keyframe允许我们定义动画中的一些关键帧,该对象主要有...

xingfeng_coder的博客 1087

Android 属性动画

Android属性动画制作,讲述一些关于属性动画制作常用的API,及简单描述如何制作属性动画,旨在引导入门。

火山的博客 2763

Android属性动画完全解析(下) Interpolator和ViewPropertyAnimator的用法

大家好,欢迎继续回到Android属性动画完全解析。在上一篇文章当中我们学习了属性动画的一些进阶技巧,包括ValueAnimator和ObjectAnimator的高级用法,那么除了这些之外,当然还有一些其它的高级技巧在等着我们学习,因此本篇文章就对整个属性动画完全解析系列收个尾,来学习一下剩下的非常重要的高级技巧。 另外,本篇文章中使用的代码是建立在上篇文章基础之上的,如果你还没有阅读过前

钢铁烈阳--非花非雾 664

Android 属性动画Interpolator和ViewPropertyAnimator的用法

转载地址:http://blog.csdn.net/guolin_blog/article/details/44171115 Interpolator的用法 Interpolator这个东西很难进行翻译,直译过来的话是补间器的意思,它的主要作用是可以控制动画的变化速率,比如去实现一种非线性运动的动画效果。那么什么叫做非线性运动的动画效果呢?就是说动画改变的速率不是一成不变的,像加速

tanghua0809的专栏 835

Android动画篇——ViewPropertyAnimator

之前我们介绍了PropertyAnimator,这一篇是之前文章的延伸。之前我们说过PropertyAnimator并不是针对View进行设计的动画类,而是为了解决对任意对象的指定属性值进行连续变换而出现的。而ViewPropertyAnimator出现的意义恰恰在于他是View而生的,他解决了View在使用属性动画时步骤繁琐,效率低下(使用PropertyAnimator为View设置多种动画,...

钟小明的专栏 811
上一篇: 4.4.1 实现点赞加一的动画animation
下一篇: 4.4.3 Android animation制作 跳动的心
千雅爸爸
博客等级 码龄18年 292粉丝 639原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值