如何将图片转换成pdfSVG转换成VectorDrawable XML资源

Android VectorDrawable SVG矢量图 xml格式 - QQtaikongyi的专栏 - CSDN博客
Android VectorDrawable SVG矢量图 xml格式
Android性能优化、系统新特性、库用法
一个VectorDrawable示例
&vector xmlns:android=//命名空间
&&& android:width=&24dp& //在设备上显示的实际宽度
&&& android:height=&24dp& //在设备上显示的实际高度
&&& android:viewportWidth=&48.0&//透视窗口宽度,与path直接相关
&&& android:viewportHeight=&48.0&//透视窗口高度,与path直接相关
&&& &path //路径1
&&&&&&& android:fillColor=&#ffffff&//路径颜色为白色
&&&&&&& android:pathData=&M8.0,19.994l32.0,0.0l0.0,8.0l-32.0,0.0z&//指令序列绘制路径(引用SVG标准)
&&& &path //路径2
&&&&&&& android:fillColor=&#ffffff&
&&&&&&& android:pathData=&M0.0,32.0l32.0,0.0l0.0,7.979l-32.0,0.0z&/&
&&&&&&& android:fillColor=&#ffffff&
&&&&&&& android:pathData=&M16.0,8.0l32.0,0.0l0.0,8.0l-32.0,0.0z&/&
VectorDrawable的作用等同于png,默认放在res/drawable路径下
SVG 是使用 XML 来描述二维图形和绘图程序的语言。
SVG 指可伸缩矢量图形 (ScalableVector Graphics)
SVG 用来定义用于网络的基于矢量的图形
SVG 使用 XML 格式定义图形
SVG 图像在放大或改变尺寸的情况下其图形质量不会有所损失
SVG 是万维网联盟的标准
SVG 与诸如 DOM 和 XSL 之类的 W3C 标准是一个整体
SVG1.1 于 2003 年 1 月 14 日成为 W3C 推荐标准。
SVG 可被非常多的工具读取和修改(比如记事本)
& & & Android系统下可以方便地修改矢量图的颜色、长宽等
SVG 与 JPEG 和 GIF 图像比起来,尺寸更小,且可压缩性更强。
SVG 是可伸缩的
SVG 图像可在任何的分辨率下被高质量地打印
& & Android系统下矢量图无需创建多个分辨率的图片)
SVG 可在图像质量不下降的情况下被放大
SVG 图像中的文本是可选的,同时也是可搜索的(很适合制作地图)
SVG 可以与 Java 技术一起运行
SVG 是开放的标准
SVG 文件是纯粹的 XML
VectorDrawable矢量图采用的标准相当于是SVG标准的子集,有些操作并不在android系统中得到支持。
.cn/svg/svg_intro.asp
http://www.w3.org/TR/SVG11/paths.html#PathData
Vector Drawable官网:
/training/material/drawables.html
/reference/android/graphics/drawable/VectorDrawable.html
/reference/android/graphics/drawable/AnimatedVectorDrawable.html
Vector、PNG、BMP等格式转换和查看工具:
http://inloop.github.io/svg2android/
AndroidStudio/AI(Adobe Illustrator)/CorelDRAW/inkscape/CAD
我的热门文章6551人阅读
移动开发(30)
首先给介绍一个网站,可谓是牛B闪闪:,有了它,麻麻再也不担心我没有图标了。如下图:
任意点击一个分组,可以见到如下各种详细的图标,我们可以根据自己的需求,调整不同的大小,然后下载图标。
当我们点击下载的时候,可以根据需要选择一种图标的颜色;但是我们会发现,有两个按钮,一个SVG,一个png,png就不用多说了,直接下载之后拽到自己的资源文件就好,这里我们选择SVG按钮。
然后会下载一个以.svg后缀的文件,如下图
在浏览器中打开这个文件,即可看下如下图标
看看该文件的源代码,是如下的XML文件
&?xml version="1.0" encoding="utf-8"?&
&!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"&
style="width:308height:308" version="1.1" id="图形" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="1024px" height="1024px" viewBox="0 0 " enable-background="new 0 0 " xml:space="preserve"&
class="svgpath" data-index="path_0" fill="#56abe4" d="M512... 11........248 22....395-22..........219 8....465-8.266-0..........328156z" /&
然而这个并不是android中能够使用的XML文件,如何将这个xml转化为一个android能使用的VectorDrawable资源呢。
首先介绍个工具:,解压后如下图,一个静态的网页:
在浏览器中打开index.html,效果如下:
点击蓝色框框住的按钮,然后选择刚刚下载的.svg文件,即可得到如下的转换:
红色框的那个单选按钮一定要选上,否则xml在android中将无效。
然后点击download按钮保存该文件,就得到一个android能使用的VectorDrawable了
&?xml version="1.0" encoding="utf-8"?&
xmlns:android="/apk/res/android"
android:width="1024dp"
android:height="1024dp"
android:viewportWidth="1024"
android:viewportHeight="1024"&
android:fillColor="#56abe4"
android:pathData="M512.333,273.328 C518.237,273.328,523.891,275.703,528.023,279.919
L952.764,713.295 C961.257,721.961,961.117,735.871,952.45,744.365
C943.784,752.856,929.874,752.719,921.379,744.052 L512.333,326.687
L103.286,744.052 C94.,80.,72.
C63.,63.,71. L496.641,279.919
C500.774,275.703,506.427,273.328,512.333,273.328 Z" /&
使用方式及效果图如下:
调整大小。
默认的图片是的,我们可以调整xml中的width和height去改变图片的大小,再也不用为了调个大小,还得去跪舔一遍UI妹子。
到这里,你是不是会觉得,这…这…还要个毛的UI啊!任意图标都不在话下……
&&相关文章推荐
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
访问:104450次
积分:1319
积分:1319
排名:千里之外
原创:36篇
评论:30条
(1)(3)(2)(1)(2)(1)(9)(4)(1)(1)(4)(5)(5)(1)
(window.slotbydup = window.slotbydup || []).push({
id: '4740881',
container: s,
size: '200,200',
display: 'inlay-fix'转载请注明出处:
项目需要 要在快速设置面板里显示一个VoWiFi图标(为了能够区分出来图形,我把透明的背景填充为黑色了)
由于普通图片放大后容易失真,这里我们最好用矢量图(SVG(Scalable Vector Graphics))来做图标,而系统状态栏图标多是用vectorDrawable绘制,所以我们的最终目的就是绘制一个上图中样式的Android
VectorDrawable xml图标。尤其是这种资源文件体积小放大又不失真,干嘛不用呢。
VectorDrawable
Android L开始提供了新的API&VectorDrawable&可以使用SVG类型的资源,也就是矢量图。在xml文件中的标签是&vector&
google官方API介绍:
This lets you create a drawable based on an XML vector graphic. It can be defined in an XML file with the&&vector&&element.
The vector drawable has the following elements:
具体属性和方法请参考官方说明
下面是一个官方例子:
&vector xmlns:android=&/apk/res/android&
android:height=&64dp&
android:width=&64dp&
android:viewportHeight=&600&
android:viewportWidth=&600& &
android:name=&rotationGroup&
android:pivotX=&300.0&
android:pivotY=&300.0&
android:rotation=&45.0& &
android:name=&v&
android:fillColor=&#000000&
android:pathData=&M300,70 l 0,-70 70,70 0,0 -70,70z& /&
&/group& &/vector&
显示效果(背景色应为透明)
如果想了解绘制原理,调至请调至文末点击W3C的连接。
接下来介绍一些常用的svg绘图工具
1.Inkscape
开源的多平台矢量图绘图工具,支持windows OS X Linux。支持导出为svg等格式图片,功能强大,与后面两个将要介绍的比较就是体积有点大,安装包就接近百兆了。
另外用这个生成的SVG文件,会带一些默认的属性,转化成VectorDrawable以后xml文件里也会有一些默认的属性,虽不影响显示效果,但会多出一些不必要的代码。
工作界面:
2.Boxy SVG
是一个Chrome应用(推荐)。支持导入,另存为,可以选中单个控件调整属性等。可能不好的地方就是你得安装Chrome浏览器吧,还有下载这个应用的时候得翻墙。
3.Janvas - The Online Vector Graphics Editor
也是Chrome应用,不过其实就是一个链接,打开后指向下面的地址
但是这个在线编辑器好像只能打开和保存文件到google driver,不推荐
这个东西没找到名字,点击下面的连接试用。添加到收藏夹,随时可用。便捷。
转换为VectorDrawable
找到两个在线转换的工具,都是Github上的开源项目。
1.Android SVG to VectorDrawable
Convert SVG to Android VectorDrawable XML resource
可能是这个工具开发比较早,有很多Star,基本的图形转换是可以的,但是,不支持文字!也就是说上面的图,如果我们转换的话,得到的结果只是一个椭圆,文字会丢失。
在线工具:
源码地址:
2.SvgToVectorDrawableConverter.Web
converter of SVG images to Android VectorDrawable XML resource files.
这个就比较好了,支持文本转换。
在线工具:
源码地址:
这里我把颜色改回了白色。使用的是Boxy SVG绘制,SvgToVectorDrawableConverter.Web转换。
Android Studio支持直接预览VectorDrawable矢量图,有了实时预览,也方便进行一些简单的修改。
这个图标最后应用到下拉的快速设置里面,在手机上的效果图就不上了。
展示一张稍复杂的图吧:
本文简单介绍了几款工具,目的能让新手快速的了解一下如何制作出自己需要的矢量图资源文件,在有需要做一张应用到Android应用/系统的矢量图时不至于措手不及。当然如过你牛逼到直接用记事本“绘图”的话,本文应该不适合你。
我发现我特别喜欢发掘一些能够提高生产力的小工具啊,哈哈哈。
知其然不知其所以然?想要了解的原理,跳转到W3C查看Scalable Vector Graphics (SVG) 1.1 (Second Edition)
本文已收录于以下专栏:
相关文章推荐
Vector矢量图在Android项目中的应用越来越广泛,但是如果你想用Android Studio自带的工具将SVG图片转化成Vector资源文件却是相当麻烦,首先能支持的SVG规范较少,其次操作流...
这个效果我们需要考虑以下几个问题:
1. 这是图片还是文字;
2. 如果是图片该如何拿到图形的边沿线坐标,如果是文字呢?
3. 如果拿到了边沿线坐标,如何让光线沿着路径跑动;
4. 怎么处理过程的衔接...
为啥要使用?
安卓开发过程中,经常使用到png格式的图片资源,这种图片需要有不同分辨率来做屏幕适配,当图片数量很大时,被打包的图片资源占据了app的绝大部分容量,使用Vector来创建图片,将大大减少...
一、SVG相关工具在线SVG编辑器
Method Draw:http://editor.method.ac
svgedit:/SVG-Edit/svgedit离...
首先给介绍一个网站,可谓是牛B闪闪:阿里巴巴矢量图标,有了它,麻麻再也不担心我没有图标了。如下图: 任意点击一个分组,可以见到如下各种详细的图标,我们可以根据自己的需求,调整不同的大小,然后下载图标。...
VectorDrawableAndroid L开始提供了新的API VectorDrawable 可以使用SVG类型的资源,也就是矢量图,这里对VectorDrawable和SVG做一些简要的介绍。
VectorDrawable
Android L开始提供了新的API VectorDrawable 可以使用SVG类型的资源,也就是矢量图。在xml文件中的标签是,下面是一个例子
vector xm...
1.效果图2.SVG-Path路径下面的命令可用于路径数据:M = movetoL = linetoH = horizontal linetoV = vertical linetoC = curve...
他的最新文章
讲师:王哲涵
讲师:韦玮
您举报文章:
举报原因:
原文地址:
原因补充:
(最多只允许输入30个字)Android动画总结系列(6)——矢量图形与矢量动画
时间: 21:37:27
&&&& 阅读:365
&&&& 评论:
&&&& 收藏:0
按照我一开始的打算,上面一篇文章应该是“Android动画总结系列(5)——属性动画源码分析”,不过属性动画源码分析写起来还比较复杂,因为某些原因,我把精力投入到矢量动画这块了,第5篇估计会在后面一两周写完。本篇文章,我写的是Android5.0引入的新动画效果——矢量动画,初步打算后面还会加一篇源码分析。
Android应用的不断发展带来了安装包过大的尴尬,而Android之前一直都不支持矢量图形,是引起尴尬的一个重要原因。其实Android绘制界面时也是通过各种类似矢量图形命令操作完成的,所以Android最终在Lolliop引入矢量图形既是大势所趋,也是水到渠成的一件事情。矢量图有很多标准,Android支持的是SVG标准(可缩放矢量图形Scalable Vector Graphics)。但不是全量支持,准确的说Android支持的是SVG标准中Path相关的部分。
SVG是通用的矢量图标准,我们可以很轻易的从Photoshop之类的软件导出想要的图形。导出的文件后缀是*.svg,这个文件的内容是文本格式的,用txt文件查看就可以打开,其内部是一系列遵循SVG规范的命令列表。
SVG Path的路径是一系列的命令组成的,每条命令告诉绘图系统,如何绘制路径。命令的写法:
1)每条命令之间可以用换行/空格/逗号进行分隔;
2)每条命令内的命令和其参数之间可以用换行/空格/逗号分隔,也可以直接连在一起;
3)命令的各个参数间可以用换行/空格/逗号分隔;
通常如果路径过长,为便于阅读,建议命令之间用换行,命令与参数之间用空格,参数之间用逗号进行分隔。
1.2 Path命令定义与用法
Android支持的路径命令包括:
M: move to 移动到绘制点
用法:M X,Y (X,Y)是Canvas上的点的位置,M命令会改变Path的初始点 ,如M 10,10或者 M10 10,Path从(10,10)开始绘制。
对应android.graphics.Path的void moveTo(float x, float y)方法。
L:line to 绘制直线
用法:1)L X,Y 从当前位置绘制直线到(X,Y),如L 10,10或者L10 10
& & & & & 2)对于水平方向和垂直方向绘制直线的时候,L命令有两个简化表达法,H X表示水平连接,V Y表示垂直连接,比如M 10,10H12表示的是从(10,10)绘制一条直线到(12,10),M10,10V12表示从(10,10)绘制一条直线到(10,12)。
对应Path类void lineTo(float x, float y)方法。
Z:close 闭合,没有参数,表示用直线连接Path的初始点和Path的终点。
用法:一般Z命令用在一条Path的最末尾,但其实在Z命令后还可以再继续新的路径,不过Z命令不改变Path的初始点,所以M2,2L5,5L5,10ZL6,4L7,3Z命令第二个Z认为的Path初始点还是(2,2),如果是M2,2L5,5L5,10ZM3,2L6,4L7,3Z命令,则第二个Z认为的Path起始点是(3,2)。
对应Path类的void close()方法。
C:cubic bezier 绘制三次贝塞尔曲线
用法:C X1,Y1 X2,Y2 X,Y 从当前点到(X,Y)点绘制一条控制点是(X1,Y1)、(X2,Y2)的三次贝塞尔曲线,如C 6,4, 7,4, 10,5,控制点是(6,4)、(7,4),最终点是(10,5)。
对应Path类的void cubicTo(float x1, float y1, float x2, float y2,&float x3, float y3)方法,方法参数与上面定义顺序完全相同。
S:smooth cubicto绘制一条平滑的三次贝塞尔曲线
用法:S X1,Y1 X,Y 如果前面是一个C/S命令,则自动计算一个保证起始点平滑的对称控制点(X1‘,Y1‘),从当前点到(X,Y)绘制一条控制点是(X1‘,Y1‘)、(X1, Y1)的三次贝塞尔曲线。其它与上面C命令相同。
如果S前面是一个非C/S命令,则无法计算一个对称的控制点,则从当前点到(X,Y)绘制一条控制点是(X1,Y1)的二次贝塞尔曲线(降阶特性)。
Q:quatratic bezier 二次贝塞尔曲线
用法:Q x1,y1 x,y,从当前点到(x,y)绘制一条控制点是(x1,y1)的二次贝塞尔曲线,如Q 6,4 10,5,控制点是(6,4),最终点是(10,5)。
对应Path类的void quadTo(float x1, float y1, float x2, float y2)方法,参数定义与顺序同上。
T:smooth quatratic to绘制一条平滑的二次贝塞尔曲线
用法:T X,Y 如果前面是一个Q/T命令,则自动计算一个保证起始点平滑的对称控制点(X1,Y1),从当前点到(X,Y)绘制一条控制点是(X1,Y1)的二次贝塞尔曲线。其它与上面Q命令相同。
如果T前面是一个非Q/T命令,则无法计算一个对称的控制点,则从当前点到(X,Y)绘制一条直线(降阶特性)。
A:ellipse 绘制一个椭圆圆弧
用法:绘制椭圆圆弧的参数比较复杂,如下:A rx ry x-axis-rotation large-arc-flag sweep-flag X Y,表示绘制一个椭圆圆弧经过(X,Y)点。
rx:椭圆横轴半径
ry:椭圆竖轴半径
x-axis-rotation:椭圆横轴相对于CanvasX轴的偏移角度
large-arc-flag:在前面三个参数确定的情况下,满足当前点到指定点(X,Y)位置条件的圆弧总是有四条,此值取0表示绘制小弧度,取值1表示绘制大弧度
sweep-flag:在前面三个参数确定的情况下,满足当前点到指定点(X,Y)位置条件的圆弧总是有四条,去掉上面large-arc-flag标识后还有两个,sweep-flag 取值0表示绘制逆时针方向的圆弧,取值1表示绘制顺时针方向的圆弧。
盗个图(来源)来辅助表达:
举例:M5,5,A 3,2 0 1 1 5 5.00001 此命令基本上绘制了一个完整的椭圆。注意如果写成M5,5,A 3,2 0 1 1 5 5就什么都展示不了了,因为两点完全相等,命令的目标连接两点已经达到,就不绕大弯子了,所以此处或者目标X或者目标Y要做一点细微的区别。
此命令对应的是void arcTo(float left, float top, float right, float bottom, float startAngle,&float sweepAngle, boolean forceMoveTo),不过参数需要做转化。
这里列出的每个命令还有对应的小写形式,上面的大写字母代表后面的参数是绝对坐标,而小写字母表示相对坐标。
假如当前绘图位置是X0,Y0,则:
M x, y 对应的是 m x-X0, y-Y0;小写形式对应的是Path类的void rMoveTo(float dx, float dy)。
L x, y 对应的是 l x-X0, y-Y0;小写形式对应的是Path类的void rLineTo(float dx, float dy)。
Z 对应的是z,两者作用相同;大小写形式对应的都是Path类的void close()。
C x1,y1 x2,y2 x,y 对应的是 c x1-X0, y1-Y0, x2-X0, y2-Y0 x-X0, y-Y0;小写形式对应的是 Path类的void rCubicTo(float x1, float y1, float x2, float y2, float x3, float y3)。
Q x1,y1 x,y 对应的是 q x1-X0, y1-Y0 x-X0,y-Y0;小写形式对应的是Path类的rQuadTo( float dx1, float dy1, float dx2, float dy2)。
A rx ry x-axis-rotation large-arc-flag sweep-flag x y 对应的是&A rx ry x-axis-rotation large-arc-flag sweep-flag x-X0 y-Y0,小写形式在Path类中与大写方式对应接口的相同,都需要做参数转化。
1.3 SVG与Android XML的转化
&提供了将SVG转化为android的XML文件的在线工具。
不过要注意一点,因为Android不完全支持SVG标准,所以svg2android的项目会丢弃很多信息,诸如渐变之类的。
同时在转化某些非path协议时,转化效果也有点细节问题。比如转化svg的ellipse时,它用了一系列的贝塞尔曲线Path来拟合椭圆,更简化的方法应该是使用A命令来生成椭圆。所以这个工具也不是万能的,大家不能全靠工具来生成xml。
还要注意,工具生成的xml内width/height属性直接使用svg的画布尺寸的,单位是dp,这样的drawable可能会导致性能问题,所以要记得改成自己需要的宽高。
二、矢量图形
2.1 XML定义
矢量图形对应的XML文件定义在res/drawable下,在XML文件中的根标签是&vector&。
vector支持drawable相关的属性,如width/height等(必须要设置,否则View是wrap_content时drawable没宽高无法运行),还支持一些特定属性,关键的有viewportWidth/viewportHeight,这两个值代表虚拟画布的宽高,后面的Path绘制里的参数都是相对此画布的宽高坐标系进行的。具体的属性见下面2.2节。
vector标签下支持0个或多个&group&标签,表示一组路径的集合,在&group&内定义一个或多个&path&标签,定义要被绘制的路径,也可以不加&group&,直接在&vector&下定义一个或多个&path&标签,这些path路径标签支持fillColor(填充颜色)/pathData(路径)/strokeWidth/strokeColor等属性。&group&/&path&标签下还支持&clip-path&标签。
如果要绘制的一块区域,就使用填充颜色fillColor,则路径起始点到路径绘制的所有点的都有填充,如果要绘制的是路径,则使用strokeWidth/strokeColor,不使用fillColor,来绘制路径。
定义好一个XML后,就可以当正常的drawable资源使用了。下面是一个网上找到的心形路径的XML定义:
&vector xmlns:android=&/apk/res/android&
android :width=&256dp&
android :height=&256dp&
android :viewportHeight=&32&
android :viewportWidth=&32&&
android:fillColor= &#8f00&
android:pathData= &M20.5,9.5
c-1.955,0,-3.83,1.268,-4.5,3
c-0.67,-1.732,-2.547,-3,-4.5,-3
C8.957,9.5,7,11.432,7,14
c0,3.53,3.793,6.257,9,11.5
c5.207,-5.242,9,-7.97,9,-11.5
C25,11.432,23.043,9.5,20.5,9.5z& /&
pathData内的路径命令列表代表的是一个心形图案的展示。命令以M命令指定绘制点初始点开始,到z命令封闭路径结束。pathData内支持上文提到的各种命令。将svg文件中path部分复制到此处,可以定义一个Android支持的矢量图形。效果如下:
2.2 特性描述
2.1.1 概述
矢量图形对应的Java类是VectorDrawable。VectorDrawable没有提供setPathData之类的方法,所以我们只能在XML内定义矢量图形。
为了优化重绘性能,每个VectorDrawable维护了一个Bitmap缓存。因此,使用同一个VectorDrawable的时候,引用的是同一个Bitmap缓存,如果两个引用位置要求不同的图像大小,每次大小发生变化的时候,bitmap都需要重新创建并重新绘制,这是一个非常大的开销。所以,如果一个VectorDrawable在不同的时机需要不同的大小,更高效的方法是创建多个VectorDrawable,这样每个Size都有一个VectorDrawable,从而减少bitmap操作导致的开销。
2.1.2矢量图形的xml标签与属性
矢量图形的xml文件支持以下标签:
&vector&:根标签,表示一个矢量动画
支持的属性:
1)android:name:定义矢量图形的名称
2)android:width:定义Drawable的宽度,支持所有dimension单位,一般使用dp。drawable的宽度不一定是最终绘制宽度,比如给ImageView设置backgroud则Drawable绘制宽度等于ImageView的宽度,给ImageView设置src则在ImageView大于Drawable宽度时,Drawable绘制宽度等于自己定义的宽度。
3)android:height:定义Drawable的宽度,支持所有dimension单位,一般是dp。其它同上。
4)android:viewportWidth:定义矢量图形的视图(viewport)空间的宽度,viewport是一个虚拟的canvas,后面所有的path都在该坐标系上绘制。坐标系左上方为(0,0),横轴从左向右,纵轴从上到下。横轴可视区域就是0~viewportWidth。
5)android:viewportHeight:定义矢量图形的可视区域的高度。其它见上。[0,0]~[viewportWidth,viewportHeight]定义了虚拟canvas的可视区域。
6)android:tint:作为染色(tint)的色彩应用到drawable上。默认不应用tint。
7)android:tintMode:tint颜色的Porter-Duff混合模式,默认是src_in。
8)android:autoMirrored:如果drawable布局方向是RTL(right-to-left)时,drawable绘制是否需要镜像化(镜像化就是绕自身x轴中线旋转180度)。
9)android:alpha:drawble的透明度,取&#
&group&:定义一组路径和子group,另外还定义了转换信息(transformation information)。转换信息定义在vector指定的视图区域内(与viewport坐标系相同)。定义的应用转换的顺序是缩放--&旋转--&平移,所以同时定义的这些属性最先应用scaleX/scaleY属性,最后应用translateX/translateY属性。
支持的属性:
1)android:name:定义group的名称
2)android:rotation:group对应矢量图形的旋转角度,取值是360度制。
3)android:pivotX:Group旋转和缩放时的中心点的X轴坐标。取值基于viewport视图的坐标系,不能使用百分比。
4)android:pivotY:Group旋转和缩放时的中心点的Y轴坐标。取值基于viewport视图的坐标系,不能使用百分比。
5)android:scaleX:Group在X轴上的缩放比例,最先应用到图形上。
6)android:scaleY:Group在Y轴上的缩放比例,最先应用到图形上。
7)android:translateX:Group在X轴的平移距离,取值基于viewport视图的坐标系。最后应用到图形上。
8)android:translateY:Group在Y轴的平移距离,取值基于viewport视图的坐标系。最后应用到图形上。
&path&:定义一个路径,一个路径即可以表示一块填充区域也可以表示一根线条。
支持的属性:
1)android:name:定义路径的名称
2)android:pathData:定义路径的数据,路径由多条命令组成,格式与SVG标准的path data的d属性完全相同,路径命令的参数定义在viewport视图的坐标系。
3)android:fillColor:指定填充路径的颜色,一般是一个颜色值,在SDK24及以上,可以指定一个颜色状态列表或者一个渐变的颜色。如果在此属性上做渐变动画,新的属性值会覆盖此值。如果不指定,则path不被填充。
4)android:strokeColor:指定路径线条的颜色,一般是一个颜色值,在SDK24及以上,可以指定一个颜色状态列表或者一个渐变的颜色。如果在此属性上做渐变动画,新的属性值会覆盖此值。如果不指定,则path的线条不会绘制出来。
5)android:strokeWidth:指定路径线条的宽度,基于viewport视图的坐标系(不要dp/px之类的结尾)。
6)android:strokeAlpha:指定路径线条的透明度。
7)android:fillAlpha:指定填充区域的透明度。
8)android:trimPathStart:取值从0到1,表示路径从哪里开始绘制。0~trimPathStart区间的路径不会被绘制出来。
9)android:trimPathEnd:取值从0到1,表示路径绘制到哪里。trimPathEnd~1区间的路径不会被绘制出来。
10)android:trimPathOffset:平移可绘制区域,取值从0到1,线条从(trimPathOffset+trimPathStart绘制到trimPathOffset+trimPathEnd),注意:trimPathOffset+trimPathEnd如果超过1,其实也是绘制的的,绘制的是0~trimPathOffset+trimPathEnd-1的位置。
11)android:strokeLineCap:设置线条首尾的外观,三个值:butt(默认,向线条的每个末端添加平直的边缘), round(向线条的每个末端添加圆形线帽), square(向线条的每个末端添加正方形线帽。)。
12)android:strokeLineJoin:设置当两条线条交汇时,创建什么样的边角(线段连接类型):三个值:miter(默认,创建尖角),round(创建圆角),bevel(创建斜角) 。
13)android:strokeMiterLimit:设置设置最大斜接长度,斜接长度指的是在两条线交汇处内角和外角之间的距离。只有当 lineJoin 属性为 &miter& 时,miterLimit 才有效。从盗了个图:
14)android:fillType:设置路径的填充类型,与SVG格式的&fill-rule&属性相同。见https://www.w3.org/TR/SVG/painting.html#FillRuleProperty。
&clip-path&:定义当前裁切的路径。裁切路径只能用于当前group和其子元素,只有在裁切路径内的元素才会被显示出来。clip-path定义后才会影响后面path的绘制,如果一个group内有多个path,clip-path定义在第三位,则前面两个path不受其影响,后面的path受其影响。如果希望clip-path对整个group都生效,应放在第一位。
支持的属性:
1)android:name:定义裁切路径的名称
2)android:pathData:定义裁切路径,取值与上面讲的pathData相同。
2.3 一个简单的笑脸(vector_drawable_smile_face.xml)
&vector xmlns:android=&/apk/res/android&
android :width=&100dp&
android :height=&100dp&
android :alpha=&2&
android :viewportHeight=&100&
android :viewportWidth=&100&&
android:name= &test&
android:pivotX= &50&
android:pivotY= &50&&
android:name=&face&
android:fillColor=&#ffff00&
android:pathData=&M50,10
A40,40 0 1 1 50,90
A40,40 0 1 1 50,10& /&
android:name=&left_eye&
android:fillColor=&#000000&
android:pathData=&M30,30
A5,5 0 1 1 40,30
A5,5 0 1 1 30,30& /&
android:name=&right_eye&
android:fillColor=&#000000&
android:pathData=&M60,30
A5,5 0 1 1 70,30
A5,5 0 1 1 60,30& /&
android:name=&nose&
android:pathData=&M50,40
C55,55 30,58 55,55&
android:strokeColor=&#000000&
android:strokeWidth=&2& /&
android:name=&mouth&
android:pathData=&M35,80
Q50,65 65,80&
android:strokeColor=&#000000&
android:strokeWidth=&2& /&
三、矢量动画
首先要说明一点:矢量动画其实是属性动画系统的一个应用。
矢量动画可以有多种动画效果:
group对应的旋转/缩放/平移等效果是传统的动画效果。
path对应的属性可以做出很多绚丽的效果。比如改变pathData属性,可以做出形状变化的动画;改变trimPathStart/trimPathEnd可以做出绘制曲线路径的效果;改变strokeColor可以做出线条颜色变化的效果。
clip-path的pathData变化可以做出各种形状的揭开和遮挡的效果。
3.1 XML定义
XML定义一个矢量动画需要完成三部曲:
1)在res/drawable内定义一个矢量图形 &vector&
2)在res/drawable内定义一个矢量动画drawable &animated-vector&
3)定义2中使用的属性动画 &objectAnimator&
3.1.1 定义矢量图形
在XML中定义一个矢量动画,首先需要在res/drawablen内定义一个矢量图形的XML。下面定义了一个三角形的XML(对应Java类VectorDrawable):
&vector xmlns:android=&/apk/res/android&
android :height=&200dp&
android :width=&200dp&
android :viewportHeight=&100&
android :viewportWidth=&100& &
android:name= &rotateGroup&
android:pivotX= &50.0&
android:pivotY= &50.0& &
android:name=&triangle1&
android:fillColor=&#00ff00&
android:pathData=&M50,30
L 50,30 L 70,70 L 30,70 z& /&
android:name=&triangle2&
:strokeColor=&#ff0000&
android:pathData=&M30,80
L 30,80 L 70,80 L 50,90 z& /&
我们注意到,上面这个矢量图内包含一个group标签,和2个path标签。group可以包含多个path标签。这些标签都做了命名,后面我们需要用标签的名称找到矢量图形内的对象,并对其做动画。
另外,看pathData部分,我们本来一个三角形的定义只需要M50,30& L 70,70 L 30,70 z即可,这里多了一个无意义的L 50,30是干嘛的呢?这个我们后面再说。
3.1.2 定义矢量动画
矢量图形定义好了后,我们就需要指定矢量动画了。矢量动画在XML中对应的标签是&animated-vector&,其XML文件也定义在res/drawable内,所以本质上也是一个drawable资源,可以在布局中随意使用。矢量动画可以对上面的矢量图形的整体或者一部分做动画效果。也就是对&group&或&path&元素做动画。
对上图的整体做效果,其实就是对rotateGroup做动画,而对部分图形做效果,我们选用第一个三角形triangle1,让它过渡成一个矩形。下面是矢量动画的定义(res/drawable/news_animator_drawable.xml):
&animated-vector xmlns:android=&/apk/res/android&
android:drawable=&@drawable/news_animation_vector& &
android:name= &rotateGroup&
android:animation=&@animator/rotate_animator& /&
android:name= &triangle1&
android:animation=&@animator/path_change& /&
&/animated-vector &
可以看出,一个矢量动画,包含了多个&target&标签,每个target标签其实就是对上面定义的矢量图形的整体或者局部指定动画效果,如何确定对那块图形做动画,就靠上面定义的矢量图形块中定义的名称(android:name)字段了。对group和path的命名,帮助系统在动画执行前从矢量图形内找到它们。
3.1.3 定义属性动画
上面我们讲到,矢量动画是属性动画的一个应用。我们可以看到,每个target指定的动画标签都是一个属性动画。我们来看下这两个矢量动画的定义,rotate_animator动画用于整体矢量图形旋转,path_change动画用于将三角形转化成四边形:
&objectAnimator xmlns:android=&/apk/res/android&
android:duration=&3000&
android:propertyName=&rotation&
android:valueFrom=&0&
android:valueTo=&360& /&
&objectAnimator xmlns:android=&/apk/res/android&
android :duration=&3000&
android :propertyName=&pathData&
android :valueFrom=&M50,30
L 50,30 L 70,70 L 30,70 z&
android :valueTo=&M30,30 L 70,30 L 70,70 L 30,70 z&
android :valueType=&pathType& /&
上面一个属性动画我们很熟悉了,以前讲的时候这种旋转都是应用在View上,这次是应用在矢量图形的group上,这说明矢量图形的group标签对应的java类有类似setRotation()之类的接口做图形旋转 。
下面这个属性动画我们比较陌生,不过其本质还是属性动画对类型为pathType的对象属性值做插值。既然是插值,我们就需要两者具有可比性,所以valueFrom和valueTo的值内的命令列表必须一一对应(每条命令的参数个数也必须相同),插值工作才能进行,这也就是上文中我们定义了一个无意义的L50,30命令的价值所在。
每次插值的结果,都会被设置到矢量图形&path&标签的pathData属性中,这样界面刷新时,矢量图形指定path绘制的图案就不断的刷新,从而产生动画效果。
注意:再强调一遍,矢量动画要求初始帧的路径命令序列(valueFrom)与结束帧的路径命令序列(valueTo)内的命令必须一一对应,只有参数值可以不同,这样才能插值,从而矢量动画才能执行。否则编译后运行时就崩溃了。
3.1.4 集成运行动画
这时候,矢量动画已经定义好了,怎么把它集成到View内执行动画呢?
1)首先给一个ImageView定义src为刚刚定义的矢量动画drawable:
&ImageView
android :id=&@+id/imageview&
android :layout_width=&wrap_content&
android :layout_height=&wrap_content&
android:src=&@drawable/news_animator_drawable&
android :layout_marginTop=&10dp&
android :background=&#88aa88&/&
2)在Java代码内,通过取到AnimatedVectorDrawable,执行动画:
AnimatedVectorDrawable animatedVectorDrawable =
(AnimatedVectorDrawable) mImageView.getDrawable();
if(animatedVectorDrawable.isRunning()) {
animatedVectorDrawable.stop();
animatedVectorDrawable.start();
然后一个矢量动画就运行起来喽!这段代码是不是和帧动画的启动完全一致,对吧!因为它们都是Drawable的子对象,用法都差不多。
3.1.5 给笑脸做个动画
&animated-vector xmlns:android=&/apk/res/android&
android :drawable=&@drawable/smile_face&&
android:animation=&@animator/anim_smile_left_eye&
android:name= &left_eye&/&
android:animation=&@animator/anim_smile_nose&
android:name= &nose&/&
android:animation=&@animator/anim_smile_mouth&
android:name= &mouth&/&
&/animated-vector &
&!--anim_smile_left_eye.xml--&
&objectAnimator xmlns:android=&/apk/res/android&
android :duration=&1000&
android :propertyName=&pathData&
android :valueFrom=&M30,30 A5 ,5
0 1 1 40,30 A5 ,5
0 1 1 30,30&
android :valueTo=&
M34,30 A1 ,1
0 1 1 36,30 A1 ,1
0 1 1 34,30&
android :valueType=&pathType& /&
&!--anim_smile_mouth.xml--&
&objectAnimator xmlns:android=&/apk/res/android&
android :duration=&1000&
android :propertyName=&pathData&
android :valueFrom=&M35,80 Q50,65 65,80&
android :valueTo=&M35,80 Q50,90 65,80&
android :valueType=&pathType& /&
&!--anim_smile_nose.xml--&
&objectAnimator xmlns:android=&/apk/res/android&
android :duration=&1000&
android :propertyName=&trimPathEnd&
android :valueFrom=&0.2&
android :valueTo=&1&
android :valueType=&floatType& /&
3.2 路径绘制过程动画
矢量图形的path标签绘制时,存在两个属性trimPathStart、trimPathEnd,对这两个属性做属性动画可以得到路径轨迹不断绘制的效果,以第2个三角形triangle2为变化对象:
在矢量动画定义的animated-vector中加入:
android :name=&triangle2&
android:animation=&@animator/trimpathend_change& /&
定义一个新的属性动画trimpathend_change.xml:
&objectAnimator xmlns:android=&/apk/res/android&
android :duration=&3000&
android :propertyName=&trimPathEnd&
android :valueFrom=&0&
android :valueTo=&1&
android :valueType=&floatType& /&
动画执行后,path的trimPathEnd属性从0变化到1的过程就是路径不断绘制出来的过程。
这里要解释下什么是trimPathStart/trimPathEnd:
trimPathStart:开始路径的百分比,取值在0~1,0表示从路径开始位置绘制,整个路径都可见,1表示路径完全不绘制,整个路径不可见;
trimPathEnd:结束路径的百分比,取值在0~1,0表示绘制到路径开始位置就不绘制,其实就是路径不绘制,不可见,1表示绘制到路径结束位置,所以整个路径完全可见;
将路径的长度归一化,则一个Path绘制的可见区域应该是[trimPathStart,trimPathEnd]。
既然原理已经说清楚了,那么我们来看个稍微复杂点的例子,大家肯定看到过一种系统自带的转圈动画,箭头转圈的过程中,它后面已经绘制的圆弧不断消失,最终一圈跑下来,又归于原位。这种效果就可以用trimPathStart和trimPathEnd实现。trimPathStart是路径开始绘制的位置,trimPathEnd是路径结束绘制的位置。所以如果这两个属性都发生改变,但是trimPathStart抹去路径绘制区域的速度慢于trimPathEnd的时候会怎么样呢?是不是就造成了这种转圈效果呢?下面我就不绘制圆了,用上面的三角形triangle2做例子(res/animator/trimstartend_change.xml):
&set xmlns:android=&/apk/res/android& &
&objectAnimator
android:duration= &3000&
android:propertyName= &trimPathStart&
android:valueFrom= &0&
android:valueTo= &1&
android:valueType= &floatType& /&
&objectAnimator
android:duration= &2000&
android:propertyName= &trimPathEnd&
android:valueFrom= &0&
android:valueTo= &1&
android:valueType= &floatType& /&
效果还可以,对吧!
四、兼容性问题
4.1 VectorDrawable的png生成策略
发布于Android 5.0的VectorDrawable,有一段时间官方是不支持低版本的。
Android build tools提供一种方案,如果编译版本是5.0以下版本,则会把VectorDrawable生成对应的png图片,这样在5.0以下的版本则使用的是生成的png图,而在5.0以上的版本中则使用VectorDrawable。
大家知道,Android有多个屏幕密度(ldpi/mdpi/hdpi/xhdpi/xxhdpi....),每个都生成一个一张png,那还不如一开始就切位图呢!所以buid toos提供一个配置(build.gradle):
defaultConfig {
applicationId &org.qcode.androidsvgdemo&
minSdkVersion 9
targetSdkVersion 23
versionCode 1
versionName &1.0&
generatedDensities = [ 'hdpi', 'xhdpi' ]
minSdkVersion支持到9,此时generatedDensities生效(注意:如果minSdkVersion 21,则此属性不生效,直接使用矢量图xml)。generatedDensities = [ ‘hdpi‘, ‘xhdpi‘ ]表示只给hdpi和xhdpi生成png图片。其他密度都不生成(此属性不配置,就对所有屏幕密度都生成一份png):
这样既能兼容老版本,又能在高版本上(drawable-anydpi-v21)上使用矢量图形。
这里还要注意另一个问题,正常情况下,我们可以通过@string/**来引用pathData,但如果生成png,则使用@string/**会报错,此时pathData的内容只能写在矢量图形的xml文件内。
4.2 AnimatedVectorDrawable不兼容的解决
前面说了通过png生成来支持VectorDrawable在低版本的展示,但是AnimatedVectorDrawable没办法通过这种方式支持,所以在使用矢量动画时需要注意:如果不考虑支持5.0之前的版本,则一切OK。否则应把矢量图形资源放到 res/drawable目录中,把矢量动画放到 drawable-v21 目录中,并在drawable 中提供一个和 AnimatedVectorDrawable同名字的资源来在 5.0之前的版本使用(这个资源可以考虑使用selector来做点效果)。
4.3 开发者社区的支持
vector-compat相对比较好,不过后面google提供了官方支持,这些支持可以不用看了。
4.4 官方低版本支持
Android最终发布了官方Support包(support-vector-drawable)的VectorDrawableCompat做低版本兼容(最低支持到API 7)。所以如果我们使用VectorDrawableCompat加载矢量资源,就不需要再生成png了。
要在工程中支持低版本的矢量图形和动画,需要support0vector-drawable库和23.2.0+的appcompat-v7库(还要取消png生成,支持于android studio1.4) 。
compile ‘com.android.support:appcompat-v7:23.2.0‘编译出support-vector-drawable-23.2.0和animated-vector-drawable-23.2.0这两个库。
工程配置方面,VectorDrawableCompat需要依赖aapt的一些功能,来保持最近矢量图使用的添加的属性ID,以便他们可以被v21之前的引用。想要的在build.gradle需要增加一些配置:
如果Gradle插件版本V2.0及以上,则需要加入:
defaultConfig {
vectorDrawables.useSupportLibrary = true
如果Gradle插件版本在V1.5及以下,则需要添加:
defaultConfig {
//不生成png
generatedDensities = []
aaptOptions {
additionalParameters &--no-version-vectors&
集成时需要注意:
1)使用android:src属性的地方需要替换为app:srcCompat属性。
2)在非src属性的地方使用矢量图时,需要将矢量图用drawable容器(如StateListDrawable, InsetDrawable, LayerDrawable, LevelListDrawable, 和RotateDrawable)包裹起来使用。否则会在低版本的情况下报错。
详细的说明可以参考:
本文总结了矢量图形和矢量动画相关的知识。下面再分析下Android5.0引入矢量图形带来的改变:
矢量图形带来的好处:
1)无限拉伸不失真,免去多个屏幕密度下集成多套切片的问题,减少安装包体积
2)带来了变形动画的动画方式(矢量变形动画)
3)带来了复杂路径绘制的动画方式(矢量路径绘制动画)
矢量图形存在的缺陷:
1)兼容性问题:5.0以下版本的兼容性。
2)不完全支持SVG标准,SVG与VectorDrawable没有可比性。我们不能直接在View上展示svg格式的图片。VectorDrawable 支持SVG的一部分规则(主要是SVG中定义path部分的规则 ),我们基本上只能将svg中的Path定义的数据用在VectorDrawable的pathData中(其它标签需要工具转化成path)。
3)VectorDrawable内存有一个bitmap缓存,如果矢量图可以确定要用于不同的图像大小的场景,需要创建多个VectorDrawable,不能复用同一个VectorDrawable,否则会有性能问题。
问题虽然多多,但是矢量图形和矢量动画带来的好处是不言而喻的,它们极大的丰富了属性动画的应用场景,Android5.0后系统的动画越来越绚丽,很大程度上都与此相关。在Android应用爆炸发展的今天,精致的动画效果已经成了应用拉用户的一个很重要的方式,相信矢量动画的应用场景会越来越丰富。
参考文档:
4)&已设计好的SVG图标
8)裁切的作用
9)&VectorDrawableCompat兼容5.0以下版本
10)VectorDrawableCompat的使用与配置
&&国之画&&&& &&&&chrome插件&&
版权所有 京ICP备号-2
迷上了代码!

我要回帖

更多关于 如何将ppt转换成word 的文章

 

随机推荐