美文网首页
SVG 入门

SVG 入门

作者: linda102 | 来源:发表于2016-10-31 23:33 被阅读460次

    一、栅格图形和矢量图形
    栅格图形:也称位图,图像由一组二维像素网格表示。
    Canvas 2d API 就是一款栅格图形 API。通过 Canvas API 绘制图形,其实是更新 Canvas 的像素。PNG 和 JPEG 是两种栅格图形的格式。即 PNG 和 JPEG 图像中的数据也同样代表着像素。
    矢量图形:图像由数学描述的几何形状表示。矢量图像包括使用高级几何形状(比如线和形状)绘制图像所需的全部信息。
    SVG 是矢量图形的一种,同 HTML 一样,SVG 是一种文件格式,有自己的 API。SVG 同 DOM API 结合形成了一种矢量图形 API。尽管可以将 PNG 等栅格图形嵌入到 SVG 中,但从根本上讲,SVG 是一种矢量格式。

    二、理解 SVG
    SVG 的本质特征是它基于 XML。HTML5 引入了内连 SVG,所以 SVG 元素可以直接出现在 HTML 标记中。

    SVG 和 Canvas 的重要差异:
    (1)SVG 绘制的文本可选,而 Canvas 不能(因为 Canvas 文本用像素绘制,是图像的一部分);
    (2)SVG 上的文本是可搜索的,Canvas 上的文本无法被搜索引擎获取。

    HTML 是用来定义页面结构的声明性语言,而 SVG 是用来创建视觉结构的语言。通过 DOM API ,你可以与 SVG 和 HTML 进行交互。SVG 文档是元素构成的树状结构,同 HTML 一样,它支持脚本操作和添加样式,还可以向 SVG 元素添加事件处理函数。

    图形 API 设计方面存在两个派系:
    一是即时模式(immediate-mode):图形提供了绘图接口,由 API 接口调用引起的绘制行为会即时发生。如 Canvas。
    二是保留模式(retained-mode):在保留模式图形中,有一个与场景中的视觉对象对应的模型,它会随着时间的推移而保留下来。可以使用 API 操作场景图形,当其改变时,图形引擎会重绘场景。SVG 是一种保留模式图形,其场景图形就是文档。用于操作 SVG 的 API 是 W3C DOM API。

    SVG 文档在呈现时会保留构成它的矢量信息,缩放 SVG 时,渲染程序会立即重绘所有构成图像的线条。所以,缩放 SVG 不会导致其质量下降。而 Canvas 缩放时图像会模糊,原因是图像由像素组成,且只能在更高分辨率下重新采样。

    三、使用 SVG 创建 2D 图形
    (1)在页面中添加 SVG
    添加内联 SVG 到 HTML 页面中如同添加其他元素一样简单。svg 标签的开始标记和结束标记之间,可以添加一些形状和其他视觉对象。还可以在 HTML 中以静态图像的方式引用 SVG 文件,例如:
    <code>
    <img src="example.svg">
    </code>
    不过这种方式的缺点是:SVG 文档不能像内联 SVG 内容那样集成到 DOM 中,即无法编写与 SVG 元素进行交互的脚本。
    (2)简单的形状
    SVG 语言包含了基本的形状元素,如矩形、圆形和椭圆。形状元素的尺寸和位置被定义成了属性。如:矩形的属性有 width 和 height。圆形有一个表示半径的 r 属性。和 css 一样,距离单位包括 px,em 等。
    示例:
    <code><svg width="200" height="200">
    <rect x="10" y="10" width="100" height="80" stroke="red" fill="#ccc" />
    <circle cx="120" cy="80" r="40" stroke="#00f" fill="none" stroke-width="8" />
    </svg>
    </code>
    SVG 绘制形状对象时是按对象在文档中出现的顺序进行的。
    SVG 实用的坐标系统与 Canvas API 相同,svg 元素的左上角位置的坐标是(0,0)。
    (3)变换 SVG 元素
    SVG 中有些组织元素,可用于将多个元素结合起来,使它们作为一个整体进行变换或链接。<g> 元素代表“组”(group)。组可以用来结合多个相关的元素。组内成员可由通用 ID 来引用。此外,组也可以作为一个一个整体进行变换。示例:
    <code><svg width="200" height="200">
    <g transform="translate(-10, 350)"
    stroke-width="20"
    stroke-linejoin="round">
    <path d="M0,0 Q170,-50 260, -190 Q310, -250 410,-250"
    fill="none" />
    </g>
    </svg>
    </code>
    (4)复用内容
    SVG 中的 <defs> 元素用于定义留待将来使用的内容(折合 react/vue 中的组件功能类似)。SVG 中的 <use> 元素用于链接到 <defs> 元素定义的内容。借助这两个元素。可以多次复用同一内容,消除冗余。
    示例:
    <code><svg width="200" height="200">
    <defs>
    <g id="shapeGroup">
    <rect x="10" y="10" width="100" height="80" stroke="red" fill="#ccc" />
    <circle cx="120" cy="80" r="40" stroke="#00f" fill="none" stroke-width="8" />
    </g>
    </defs>
    <use xlink:href="#shapeGroup" transform="translate(20,0) scale(0.5)" />
    <use xlink:href="#shapeGroup" transform="translate(50,0) scale(0.7)" />
    <use xlink:href="#shapeGroup" transform="translate(80,0) scale(0.25)" />
    </svg>
    </code>
    (5)图案和渐变
    图案类似于 Canvas 中的背景图做法。渐变也分为线性渐变和放射性渐变,和 Canvas 类似。
    示例:
    <code><svg width="200" height="200">
    <defs>
    <pattern id="GravelPattern" patternUnits="userSpaceOnUse" x="0" y="0" width="100" height="67" viewBox="0 0 100 67">
    <image x="0" y="0" width="100" height="67" xlink:href:"gravel.jpg"></image>
    </pattern>
    <linearGradient id="Gradient">
    <stop offset="0%" stop-color="#000"></stop>
    <stop offset="100%" stop-color="#f00"></stop>
    </linearGradient>
    </defs>
    <rect x="10" y="10" width="100" height="80" stroke="red" fill="url(#Gradient)" />
    <circle cx="120" cy="80" r="40" stroke="#00f" fill="url(#GravelPattern)" stroke-width="8" />
    </svg>
    </code>
    (6)SVG 路径
    SVG 不仅包含简单的形状,还包含自由形态的路径。path 元素有一个 d 属性。d 代表数据(data)。在 d 属性的值中,你能够指定一系列的路径绘制命令。每条命令都可能带有坐标参数。一些命令的含义为:M 代表移至(moveto),L 代表划线至(lineto),Q 代表二次曲线, Z 代表闭合曲线。
    (7)SVG 文本
    示例:
    <code><svg width="200" height="200">
    <text x="10" y="80" font-family="Droid Sans" stroke="#00f" fill="#00f" font-size="18px">
    hello SVG
    </text>
    </svg>
    </code>

    四、组合场景
    完整示例:
    <code><svg width="400" height="600">
    <defs>
    <pattern id="GravelPattern" patternUnits="userSpaceOnUse" x="0" y="0" width="100" height="67" viewBox="0 0 100 67">
    <image x="0" y="0" width="100" height="67" xlink:href="gravel.jpg"></image>
    </pattern>
    <linearGradient id="TrunkGradient">
    <stop offset="0%" stop-color="#663300"></stop>
    <stop offset="40%" stop-color="#996600"></stop>
    <stop offset="100%" stop-color="#552200"></stop>
    </linearGradient>
    <rect x="-5" y="-50" width="10" height="50" id="Trunk"></rect>
    <path d="M-25, -50
    L-10, -80
    L-20, -80
    L-5, -110
    L-15, -110
    L0, -140
    L15, -110
    L5, -110
    L20, -80
    L10, -80
    L25, -50
    Z" id="Canopy"></path>
    <linearGradient id="CanopyShadow" x="0" y="0" x2="0" y2="100%">
    <stop offset="0%" stop-color="#000" stop-opacity=".5"></stop>
    <stop offset="20%" stop-color="#000" stop-opacity="0"></stop>
    </linearGradient>
    <g id="Tree">
    <use xlink:href="#Trunk" fill="url(#TrunkGradient)"></use>
    <use xlink:href="#Trunk" fill="url(#CanopyShadow)"></use>
    <use xlink:href="#Canopy" fill="none" stroke="#663300" stroke-linejoin="round" stroke-width="4px"></use>
    <use xlink:href="#Canopy" fill="#339900" stroke="none"></use>
    </g>
    <g id="TreeShadow">
    <use xlink:href="#Trunk" fill="#000"></use>
    <use xlink:href="#Canopy" fill="000" stroke="none"></use>
    </g>
    </defs>
    <g transform="translate(-10, 350)" stroke-width="20" stroke="url(#GravelPattern)" stroke-linejoin="round">
    <path d="M0,0 Q170,-50 260, -190 Q310, -250 410,-250" fill="none"></path>
    </g>
    <text y="60" x="200" font-family="impact" font-size="60px" fill="#996600" text-anchor="middle">
    Happy Trails!
    </text>
    <use xlink:href="#TreeShadow" transform="translate(130, 250) matrix(1, 0, -0.5, 1, 0, 0) scale(1, 0.6)" opacity="0.2"></use>
    <use xlink:href="#Tree" transform="translate(130, 250)"></use>
    <use xlink:href="#TreeShadow" transform="translate(260, 500) matrix(1, 0, -0.5, 1, 0, 0) scale(2, 1.2)" opacity="0.2"></use>
    <use xlink:href="#Tree" transform="translate(260, 500) scale(2)"></use>
    </svg>
    </code>

    相关文章

      网友评论

          本文标题:SVG 入门

          本文链接:https://www.haomeiwen.com/subject/kxaputtx.html