zoukankan      html  css  js  c++  java
  • 31、Android矢量动画

    SVG矢量动画

    (Bitmap)相对,SVG不会像位图一样因为缩放而让图片质量下降。它的优点在于节约空间,使用方便 。Android 5.0中引入了 VectorDrawable 来支持

    矢量图(SVG),同时还引入了 AnimatedVectorDrawable 来支持矢量图动画,在最近几次Support包更新之后,SVG的兼容性问题得以大大改善

    AS本身就支持SVG的加载,右击drawable,通过Vector Asset直接加载一个SVG图像。

    SVG命令

    使用<path>标签创建SVG就像使用指令的方式来控制一只画笔,它所支持的指令有以下几种:

    指令 说明
    M = moveto(M,X,Y) 将画笔移动到指定坐标位置,但未发生绘制。
    L = lineto(L,X,Y) 画直线到指定的坐标位置。
    H = horizontal lineto(H X) 画水平线到指定的X坐标位置。
    V = vertical lineto(V Y) 画垂直线到指定的Y坐标位置。
    C = curveto(C X1,Y1,X2,Y2,ENDX,ENDY) 三次贝塞尔曲线
    S = smooth curveto(S X2,Y2,ENDX,ENDY) 三次贝塞尔曲线
    Q = quadratic Belzier curve(Q X,Y,ENDX,ENDY) 二次贝塞尔曲线
    T = smooth quadratic Belzier curveto(T ENDX,ENDY) 映射前面路径的终点
    A = elliptical Arc(A RX,RY,XROTATION,FLAG1,FLAG2,X,Y) 绘制一段弧线,允许弧线不闭合。 1)RX,RY指所在椭圆大小 2)XROTATION椭圆的X轴和水平方向顺时针夹角。 3)FLAG1有两个值,1表示大角度弧线,0为小角度弧线 4)FLAG2有两个值,1位顺时针,0位逆时针 5)X,Y轴为终点坐标
    Z = closepath() 关闭路径

    在使用上面的指令时,需要注意以下几点:

    坐标轴(0,0)为中心,X轴水平向右,Y轴水平向下。
    所有指令大小写均可,大写是绝对定位,小写相对定位。
    同一个指令出现多次可以只用一个,且指令间的空格可省略。

    SVG编辑器

    SVG参数的写法固定而且复杂,因此完全可以使用程序来实现,所以一般通过SVG编辑器来编辑SVG图形。网上有很多SVG的在线编辑器,通过可视化编辑好图形后,点击View Source就可以转换为SVG代码。

    https://editor.method.ac/

    使用SVG

    在Android 5.X中提供两个新的api来支持SVG:VectorDrawable(SVG图形) 和 AnimatedVectorDrawable(动画效果)。

    • VectorDrawable
      在res/drawable/ic_verctor_test.xml中创建静态的SVG图形,其中<path>是结构中的最小单位,<group>可以将不同的<path>进行组合。
    <vector xmlns:android="http://schemas.android.com/apk/res/android"
            android:width="200dp"
            android:height="200dp"
            android:viewportWidth="100"
            android:viewportHeight="100">
            <group
                android:name="test"
                android:rotation="0">
                <path
                    android:fillColor="@android:color/holo_blue_light"
                    android:pathData="M 25 50 a 25,25 0 1,0 50, 0"/>
            </group>
    </vector>
    

    由于这里使用fillcolor表示填充,如果想要非填充的则使用:

    android:strokeColor="@android:color/holo_blue_light"
    android:strokeWidth="2"
    

    效果如下图所示:

    • AnimatedVectorDrawable

      AnimatedVectorDrawable的作用是给VectorDrawable提供动画效果,它可以连接静态的VectorDrawable和动态的ObjectAnimation。

    1、在res/drawable/anim_vector.xml中通过<animated-vector>标签声明对AnimatedVectorDrawable的使用,并指定其作用的path和group。

    <?xml version="1.0" encoding="utf-8"?>
    <animated-vector
        xmlns:android="http://schemas.android.com/apk/res/android"
        android:drawable="@drawable/ic_vector_test">
        <target
            android:name="test"
            android:animation="@animator/anim_path"/>
    </animated-vector>
    

    2、对应res/drawable/ic_verctor_test.xml中的vector是静态的VectorDrawable

    <?xml version="1.0" encoding="utf-8"?>
    <vector xmlns:android="http://schemas.android.com/apk/res/android"
        android:width="200dp"
        android:height="200dp"
        android:viewportWidth="100"
        android:viewportHeight="100">
        <group
            android:name="test"
            android:rotation="0">
            <path
                android:strokeColor="@android:color/holo_blue_light"
                android:strokeWidth="2"
                android:pathData="M 25 50 a 25,25 0 1,0 50,0"/>
        </group>
    </vector>
    

    注意:AnimatorVectorDrawable中的target节点下的name和VectorDrawable中group节点下的name必须保持一致。

    3、通过AnimatorVectorDrawable中的target节点下的animation属性引入属性动画(必须是属性动画,否则报错)

    <?xml version="1.0" encoding="utf-8"?>
    <objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
        android:duration="4000"
        android:propertyName="rotation"
        android:valueFrom="0"
        android:valueTo="360" />
    

    4、当所有的XML准备好之后,我们就可以直接给一个imageview设置背景

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical">
    
        <ImageView
            android:id="@+id/image"
            android:layout_gravity="center"
            android:layout_width="200dp"
            android:layout_height="200dp"
            android:src="@drawable/anim_vector" />
    </LinearLayout>
    

    5、最后,通过ImageView中的src引入AnimatorVectorDrawable文件,然后通过代码进行开启即可。

    ImageView imageView = (ImageView) findViewById(R.id.image);
    Animatable drawable = (Animatable) imageView.getDrawable();
    drawable.start();
    

    运行效果如下图所示:

    兼容性

    SVG在5.X以上使用是没有任何问题的,但是在低版本就会出现各种问题,可以使用如下方法进行兼容:

    兼容低版本

    我们的SVG在5.X是没有问题,但是在低版本的话可能出现彩色图片变成黑色的,解决方式如下:

    • 在build.gradle里面进行配置
    android {
        defaultConfig {
            vectorDrawables.useSupportLibrary = true
        }
    |
    
    • 只能用于AppCompatImageView或者AppCompatImageButton或其子类,而且必须在app:srcCompat标签中使用。

    • SVG图像需要依附于StateListDrawable,InsetDrawable,LayerDrawable,LevelListDrawable,RotateDrawable。StateListDrawable最简单,就是直接写一个selector即可

    ?xml version="1.0" encoding="utf-8"?>
    <selector xmlns:android="http://schemas.android.com/apk/res/android">
        <item android:drawable="@drawable/ic_a"></item>
    </selector>
    

    别忘记还有一个标志位要开启,在activity的最上方

    static {
        AppCompatDelegate.setCompatVectorFromResourcesEnabled(true);
    }
    

    动态换色

    如果你想手动更换图片的背景色,那么只要按照如下代码操作即可:

    VectorDrawableCompat a=VectorDrawableCompat.create(getResources(), R.drawable.ic_a, getTheme());
    a.setTint(Color.RED);
    ImageView imageview= (ImageView) findViewById(R.id.imageview);
    imageview.setImageDrawable(a);
    
  • 相关阅读:
    常用脚本语言Perl,Python,Ruby,Javascript一 Perl,Python,Ruby,Javascript
    Android中Linux suspend/resume流程
    Linux计算机进程地址空间与内核装载ELF
    Linux操作系统工作的基础
    Tomcat 系统架构与设计模式,第 2 部分: 设计模式分析
    基础算法题
    多模式字符串匹配(转)
    二叉树题集
    概率及数学题
    字符串算法题
  • 原文地址:https://www.cnblogs.com/pengjingya/p/14952691.html
Copyright © 2011-2022 走看看