目 录 | |
---|---|
1 | 基本属性 |
2 | path路径(SVG) |
3 | 小结 |
一、基本属性
1、笔划与填充
第一篇博文中的示例已经演示了围绕对象的笔划或线以及对象内部区域的填充.这些属性实际上还有子属性,也可以设置子属性来创建不同的效果.这些属性包括:
fill:该属性指定用来填充对象内部区域的颜料.大多数情况下,该属性只是一种颜色,但它也可以是渐变或图案(会在图案中介绍).这个值通常是关键字、颜色说明或指向预定义元素的 URI.
fill-opacity:该属性指定元素的透明性.值的范围从完全透明(0)到完全不透明(1).
stroke:该属性指定元素外边框的外观.象 fill 一样,它引用颜料,尽管通常将它指定为一种简单颜色.
stroke-width:该属性指定笔划线的宽度.
stroke-linecap:该属性确定线末端的形状,可取的值有粗端(butt)、圆(round)和正方形(square).
stroke-linejoin:该属性确定对象各角的外观.允许的值有直角(缺省值)、圆和斜角,它如示例中所示将尖角的边缘“剪掉”.
stroke-dasharray:该属性是一个整数系列(如 3、2、3、2、4、3、2 和 3),它允许对虚线中每一划的相对长度进行控制.
stroke-opacity:类似于 fill-opacity,该属性确定元素笔划线的相对透明性.
2、颜色
颜色对于 SVG 图像是极其重要的.单个颜色可以直接使用它们的 RGB 值指定,或者使用差不多 150 个颜色关键字中的一个来间接指定,该关键字也引用 RGB 值.
RGB 值在 0 到 255 数值范围内指定一种颜色的红、绿、蓝成分的相对亮度,例如:
fill=”darkorchid”;fill=”lightgrey”;
fill=”rgb(255,0,0)”;fill=”rgb(0,255,0)”; fill=”rgb(0,0,255)”;
fille=”#000000”; fill=”#ffffff”.
3、渐变
渐变提供了将颜色混合在一起的能力.
渐变有两种,<linearGradient>(线性渐变) 和 <radialGradient>(放射渐变)
对于每种情况,代码都指定沿着渐变向量的颜色“停止”或颜色点,渐变到这些点就成为某种颜色.
例如,指定红色在 0% 停止,白色在 50% 停止而蓝色在 100% 停止的渐变将逐渐由红色变为白色再变为蓝色,白色在渐变向量的中心.
<linearGradient> 和 <radialGradient> 标签必须嵌套在
A、<linearGradient>
<linearGradient>标签属性有:
id 属性是渐变定义一个唯一的名称,图形元素可通过fill=”url(linearGradientId)”来引用该线性渐变效果;
x1、x2、y1、y2 属性可定义渐变的开始和结束位置, x1,y1指定起点坐标, x2,y2指定结束坐标;
渐变的颜色范围可由两种或多种颜色组成.每种颜色通过一个
B、<radialGradient>
<radialGradient> 标签属性有:
id 属性是渐变定义一个唯一的名称,图形元素可通过fill=”url(linearGradientId)”来引用该放射渐变效果;
cx、cy 和 r 属性定义外圈,而 fx 和 fy 定义内圈;
渐变的颜色范围可由两种或多种颜色组成.每种颜色通过一个
4、图案(<pattern>)
图案 一般用于SVG图形对象的填充 fill 或描边 stroke .这个图形可以是一个SVG元素,也可以是像素图,通过 <pattern> 元素在 x 轴或 y 轴方向以固定的间隔平铺.
可以在 <pattern> 元素内定义图案,然后通过 id 引用.
<svg width="660" height="220">
<defs>
<pattern id="pattern" x="0" y="0" width="20" height="20" patternUnits="userSpaceOnUse">
<circle cx="10" cy="10" r="10" stroke="none" fill="#393" />
</pattern>
</defs>
<rect x="10" y="10" width="600" height="200" stroke="#630" stroke-width="5px" fill="url(#pattern)" />
</svg>
在 <defs> 标签内定义图案, <pattern> 元素中的内容直到引用的时候才会显示.
<pattern> 中定义一个 id,方便在后面被矩形引用.
<rect> 元素使用图案作为填充,然后再使用纯色来作为描边.
在 <pattern> 元素内 ,定义了一个半径为 10(px) 的绿色圆,cx 和 cy 的值(分别为 10px )设置了 circle 元素的初始圆的原点.
具体效果点击示例查看,下面来看看<pattern> 元素的属性:
<pattern id="pattern" x="0" y="0" width="20" height="20" patternUnits="userSpaceOnUse">
x 和 y 属性定义了图案的起点.
这里把它们都设置为0,这样在图案开始前就不会有偏移,使圆形的中心和图案的起点对齐.
width 和 height 属性定义了重复图案的宽度和高度,因为图例中是一个圆,所以设置了相同的宽高.
patternUnits 定义图案的展现方式,它的值有两个:
userSpaceOnUse: x 、 y 、 width 和 height 表示的值都是当前用户坐标系统的值,也就是说,这些值没有缩放,都是绝对值.
objectBoundingBox(默认值): x 、 y 、 width 和 height 表示的值都是外框的坐标系统(包裹pattern的元素),也就是说,图案的单位进行了一个缩放,比如:pattern中为 1 的值,会变成和包裹元素的外框的 width 和 height 一样的大小.
二、path路径
path可能是SVG中最常见的形状.你可以用path元素绘制矩形(直角矩形或者圆角矩形)、圆形、椭圆、折线形、多边形,以及一些其他的形状,例如贝塞尔曲线、2次曲线等曲线.
path只需要设定很少的点,就可以创建平滑流畅的线条(比如曲线).虽然polyline元素也能实现类似的效果,但是必须设置大量的点(点越密集,越接近连续,看起来越平滑流畅),并且这种做法不能够放大(放大后,点的离散更明显.所以在绘制SVG时,对路径的良好理解很重要.
path元素的形状是通过属性d定义的,属性d的值是一个“命令+参数”的序列
每一个命令都用一个关键字母来表示,比如,字母“M”表示的是“Move to”命令,当解析器读到这个命令时,它就知道你是打算移动到某个点.
跟在命令字母后面的,是你需要移动到的那个点的x和y轴坐标.比如移动到(10,10)这个点的命令,应该写成“M 10 10”.这一段字符结束后,解析器就会去读下一段命令.
每一个命令都有两种表示方式,一种是用大写字母,表示采用绝对定位.另一种是用小写字母,表示采用相对定位.
path标准命令:
命令 | 名称 | 参数 |
---|---|---|
M | moveto(移动到) | (x,y)+ |
Z | closepath(关闭路径) | none |
L | lineto(画线到) | (x,y)+ |
H | horizontal lineto(水平线到) | x+ |
V | vertical lineto(垂直线到) | y+ |
C | Bézier curveto(三次贝塞尔曲线到) | (x1 y1 x2 y2 x y)+ |
S | smooth curveto(光滑三次贝塞尔曲线到) | (x2 y2 x y)+ |
Q | quadratic Bézier curveto (二次贝塞尔曲线到) | (x1 y1 x y)+ |
T | smooth quadratic Bézier curveto(光滑二次贝塞尔曲线到) | (x y)+ |
A | elliptical arc(椭圆弧) | (rx ry x-axis-rotation large-arc-flag sweep-flag x y)+ |
1、直线命令
<path>元素里有5个画直线的命令,顾名思义,直线命令就是在两个点之间画直线.
首先是“Move to”命令,M,前面已经提到过,它需要两个参数,分别是需要移动到的点的x轴和y轴的坐标.
假设,你的画笔当前位于一个点,在使用M命令移动画笔后,只会移动画笔,但不会在两点之间画线.
因为M命令仅仅是移动画笔,但不画线.所以M命令经常出现在路径的开始处,用来指明从何处开始画.
能够真正画出线的命令有三个,最常用的是“Line to”命令,L,L需要两个参数,分别是一个点的x轴和y轴坐标,L命令将会在当前位置和新位置(L前面画笔所在的点)之间画一条线段.
另外还有两个简写命令,用来绘制平行线和垂直线.
H,绘制平行线.V,绘制垂直线.
这两个命令都只带一个参数,标明在x轴或y轴移动到的位置,因为它们都只在坐标轴的一个方向上移动.
<svg width="400px" height="400px" version="1.1" xmlns="http://www.w3.org/2000/svg">
<!-- 用L命令画一条直线 -->
<path d="M10 10 L 90,20 " stroke="red" stroke-width="2" />
<!-- 用H命令画一条水平直线 -->
<path d="M10 30 H 90 " stroke="green" stroke-width="2" />
<!-- 用V命令画一条水平直线 -->
<path d="M10 50 V 90 " stroke="yellow" stroke-width="2" />
</svg>
现在已经掌握了一些命令,可以开始画一些东西.
先从简单的地方开始,画一个简单的矩形(同样的效果用
<svg width="400px" height="400px" version="1.1" xmlns="http://www.w3.org/2000/svg">
<path d="M10 10 H 90 V 90 H 10 L 10 10" fill='white' stroke='red' stroke-width='2'/>
<!-- 通过“闭合路径命令”Z来简化上面的path,Z命令会从当前点画一条直线到路径的起点,Z命令不用区分大小写.-->
<path d="M110 10 H 200 V 90 H 110 Z" fill="gray" stroke="yellow" stroke-width='2'/>
</svg>
2、贝塞尔曲线命令
贝塞尔曲线(Bézier curve),又称贝兹曲线或贝济埃曲线,是应用于二维图形应用程序的数学曲线,Canvas,CSS3动画函数以及许多画图应用都离不开它.
由于数学不是很好,不能很好解释贝塞尔曲线,只好放几张图帮助理解,有兴趣可以自行Google,本文只讨论贝塞尔曲线在SVG中的用法.
线性贝塞尔曲线演示动画,t在[0,1]区间
二次贝塞尔曲线演示动画,t在[0,1]区间
三次贝塞尔曲线演示动画,t在[0,1]区间
四次贝塞尔曲线演示动画,t在[0,1]区间
五次贝塞尔曲线演示动画,t在[0,1]区间
path标签中,与贝塞尔曲线相关的命令有C命令 S命令 Q命令 T命令.
A、CS组合(三次贝塞尔曲线命令组合)
C命令和S命令是专门绘制三次贝塞尔曲线的.
上图是Photoshop中使用钢笔工具时候的截图再加工.
所谓钢笔工具抠图实际上就是一个一个贝塞尔曲线连接的结果,各类图形绘制软件类似工具本质上都是贝塞尔曲线.
图片有4个点出现,曲线的两个端点,以及两个控制点,这就是典型的三次贝塞尔曲线.
对应的path代码中就是:
<!-- 其中,d="M20,20 C90,40 130,40 180,20" -->
<!-- M20,20 表示曲线的起点 -->
<!-- C90,40 130,40 180,20 对应上图的2个控制点和1个关键点 -->
<path d="M20,20 C90,40 130,40 180,20" stroke="#000000" fill="none" style="stroke:red" >
上面代码只用到了C命令,那么S命令呢?
把关注点放在蓝线上面.S指令会自动补出一个对称的控制点(蓝线部分),于是就会有连续的平滑曲线.
对应path代码
<path d="M20,150 C60,40 80,40 120,150 S180 260 220 80" fill="none" style="stroke:yellow"></path>
B、QT组合(二次次贝塞尔曲线命令组合)
Q命令和T命令是专门绘制三次贝塞尔曲线的.
可以看到,跟三次贝塞尔曲线相比,Q命令中就是2个控制点合为1个.
与S命令类似,T命令也会自动补出一个对称的控制点(蓝线部分),生成连续的平滑曲线.
<svg id="svg" width="500" height="400">
<path d="M20 10 Q120 150 220 10 " stroke="red" fill="none" style="stroke-width: 2px;"></path>
<path d="M20 110 Q120 250 220 110 T420 110" stroke="red" fill="none" style="stroke-width: 2px;"></path>
</svg>
三、小结
本文介绍了SVG的基本属性和<path>元素的使用.
值得一提的是<path>的塞贝尔曲线指令,塞贝尔曲线属于数学范畴,或许学习成本过高,使用画图软件画出图片并用CSS控制展示不是很好吗?
然而在实际开发中,绘图是小,控制绘图为大,CSS对图片的控制力几乎没有,一旦需求出现细微变更,有可能就得重新绘图.
如果能用SVG+JS控制曲线的动画效果替代,便可以对图片进行随意的操控,将大大减少重绘的概率,项目也显得”优雅”.
图形动画领域很多东西都已一脉相承,一通百通的.动画算法也都是一致,图像处理算法也都是一致的.掌握SVG的贝塞尔曲线,肯定对于CSS3动画,Canvas的处理有很大帮助.
下篇将介绍滤镜和动画(animation).