Search K
Appearance
Appearance
关键词: SVG矢量图形, 可缩放矢量图形, SVG语法, HTML内联SVG, 矢量图形优势, SVG与Canvas, SVG基础元素, 图形标记
SVG(Scalable Vector Graphics)是一种基于XML的矢量图形格式,是HTML5的重要组成部分。SVG使用数学描述来定义图形,而不是像素点。
<!-- 最简单的SVG元素 -->
<svg width="200" height="200" xmlns="http://www.w3.org/2000/svg">
<circle cx="100" cy="100" r="50" fill="blue" />
</svg>SVG矢量图形具有以下重要优势:
<!-- 可缩放性示例 -->
<div class="svg-scalability-demo">
<h4>SVG可缩放性演示</h4>
<svg width="100" height="100" viewBox="0 0 100 100">
<rect x="10" y="10" width="80" height="80" fill="red" />
<text x="50" y="50" text-anchor="middle" dy="0.35em">小尺寸</text>
</svg>
<svg width="200" height="200" viewBox="0 0 100 100">
<rect x="10" y="10" width="80" height="80" fill="red" />
<text x="50" y="50" text-anchor="middle" dy="0.35em">大尺寸</text>
</svg>
</div><!-- SVG技术特点展示 -->
<div class="svg-features">
<h4>SVG技术特点</h4>
<svg width="400" height="300" viewBox="0 0 400 300">
<!-- 矢量图形 -->
<g id="vector-demo">
<rect x="10" y="10" width="100" height="60" fill="lightblue" stroke="blue" stroke-width="2" />
<text x="60" y="45" text-anchor="middle">矢量图形</text>
</g>
<!-- 可编辑文本 -->
<g id="text-demo">
<text x="150" y="40" font-size="16" fill="green">可编辑文本</text>
</g>
<!-- 可交互性 -->
<g id="interactive-demo">
<circle cx="300" cy="40" r="30" fill="orange" />
<text x="300" y="45" text-anchor="middle" fill="white">交互</text>
</g>
</svg>
</div>SVG和Canvas在技术特点上有明显区别:
<!-- SVG与Canvas对比展示 -->
<div class="svg-canvas-comparison">
<h4>SVG与Canvas技术对比</h4>
<div class="comparison-container">
<div class="svg-example">
<h5>SVG示例</h5>
<svg width="200" height="150" viewBox="0 0 200 150">
<rect x="20" y="20" width="160" height="110" fill="lightgreen" stroke="green" stroke-width="3" />
<text x="100" y="80" text-anchor="middle" font-size="14">SVG矢量图形</text>
</svg>
<p>特点:可缩放、可编辑、DOM结构</p>
</div>
<div class="canvas-example">
<h5>Canvas示例</h5>
<canvas id="canvasExample" width="200" height="150">
<p>Canvas位图图形</p>
<p>特点:像素绘制、高性能、脚本驱动</p>
</canvas>
</div>
</div>
</div><!-- 应用场景对比 -->
<div class="usage-scenarios">
<h4>应用场景对比</h4>
<div class="scenarios-grid">
<div class="svg-scenarios">
<h5>SVG适用场景</h5>
<svg width="150" height="100" viewBox="0 0 150 100">
<rect x="10" y="10" width="130" height="80" fill="none" stroke="blue" stroke-width="2" />
<text x="75" y="30" text-anchor="middle" font-size="12">图标设计</text>
<text x="75" y="50" text-anchor="middle" font-size="12">Logo制作</text>
<text x="75" y="70" text-anchor="middle" font-size="12">简单图表</text>
</svg>
</div>
<div class="canvas-scenarios">
<h5>Canvas适用场景</h5>
<div class="canvas-scenario-box">
<p>游戏开发</p>
<p>复杂动画</p>
<p>图像处理</p>
</div>
</div>
</div>
</div>SVG遵循XML语法规范,具有严格的结构要求:
<!-- SVG基本语法结构 -->
<svg width="300" height="200"
viewBox="0 0 300 200"
xmlns="http://www.w3.org/2000/svg">
<!-- SVG内容 -->
<rect x="10" y="10" width="100" height="80" fill="blue" />
<circle cx="200" cy="50" r="40" fill="red" />
<text x="150" y="150" text-anchor="middle" font-size="16">SVG文本</text>
</svg>SVG使用XML命名空间来定义元素:
<!-- 完整的SVG命名空间声明 -->
<svg width="250" height="180"
viewBox="0 0 250 180"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink">
<defs>
<linearGradient id="myGradient" x1="0%" y1="0%" x2="100%" y2="0%">
<stop offset="0%" style="stop-color:rgb(255,255,0);stop-opacity:1" />
<stop offset="100%" style="stop-color:rgb(255,0,0);stop-opacity:1" />
</linearGradient>
</defs>
<rect x="10" y="10" width="230" height="160" fill="url(#myGradient)" />
</svg>SVG属性遵循XML属性语法规范:
<!-- SVG属性语法示例 -->
<svg width="280" height="200" viewBox="0 0 280 200">
<!-- 基本属性 -->
<rect x="20" y="20" width="80" height="60"
fill="lightblue"
stroke="blue"
stroke-width="2" />
<!-- 样式属性 -->
<circle cx="180" cy="50" r="30"
style="fill:orange; stroke:red; stroke-width:3;" />
<!-- 变换属性 -->
<rect x="120" y="120" width="40" height="40"
fill="green"
transform="rotate(45 140 140)" />
</svg>最常见的SVG使用方式是直接嵌入HTML文档中:
<!-- 内联SVG示例 -->
<article class="svg-inline-demo">
<h4>内联SVG示例</h4>
<p>以下是一个内联SVG图形:</p>
<svg width="200" height="100" viewBox="0 0 200 100">
<rect x="10" y="10" width="180" height="80"
fill="lavender" stroke="purple" stroke-width="2" />
<text x="100" y="55" text-anchor="middle"
font-family="Arial" font-size="14" fill="darkblue">
内联SVG
</text>
</svg>
<p>SVG图形完美集成在HTML文档中。</p>
</article>SVG可以像普通图像一样使用:
<!-- SVG作为图像使用 -->
<div class="svg-as-image">
<h4>SVG作为图像使用</h4>
<!-- 使用img标签 -->
<div class="image-example">
<h5>使用img标签</h5>
<img src="example.svg" alt="SVG示例图像" width="150" height="100" />
</div>
<!-- 使用object标签 -->
<div class="object-example">
<h5>使用object标签</h5>
<object data="example.svg" type="image/svg+xml" width="150" height="100">
<p>您的浏览器不支持SVG</p>
</object>
</div>
<!-- 使用embed标签 -->
<div class="embed-example">
<h5>使用embed标签</h5>
<embed src="example.svg" type="image/svg+xml" width="150" height="100" />
</div>
</div>SVG也可以用作CSS背景图像:
<!-- SVG背景图像 -->
<div class="svg-background-demo">
<h4>SVG背景图像</h4>
<div class="bg-svg-box" style="
width: 200px;
height: 150px;
background-image: url('data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjAwIiBoZWlnaHQ9IjE1MCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj4KICA8cmVjdCB3aWR0aD0iMjAwIiBoZWlnaHQ9IjE1MCIgZmlsbD0iI2Y0ZjRmNCIvPgogIDxjaXJjbGUgY3g9IjEwMCIgY3k9Ijc1IiByPSI1MCIgZmlsbD0iI2RkZCIvPgo8L3N2Zz4=');
background-size: cover;
border: 2px solid #ccc;
">
<p style="text-align: center; line-height: 150px; margin: 0;">SVG背景</p>
</div>
</div>SVG使用自己的坐标系统,与Canvas类似但更加灵活:
<!-- SVG坐标系统演示 -->
<div class="svg-coordinate-system">
<h4>SVG坐标系统</h4>
<svg width="300" height="200" viewBox="0 0 300 200">
<!-- 坐标系统网格 -->
<defs>
<pattern id="grid" width="20" height="20" patternUnits="userSpaceOnUse">
<path d="M 20 0 L 0 0 0 20" fill="none" stroke="#ddd" stroke-width="1"/>
</pattern>
</defs>
<rect width="300" height="200" fill="url(#grid)" />
<!-- 坐标轴 -->
<line x1="0" y1="0" x2="300" y2="0" stroke="red" stroke-width="2" />
<line x1="0" y1="0" x2="0" y2="200" stroke="red" stroke-width="2" />
<!-- 坐标点标记 -->
<circle cx="0" cy="0" r="3" fill="red" />
<text x="5" y="15" font-size="12" fill="red">原点(0,0)</text>
<circle cx="100" cy="50" r="3" fill="blue" />
<text x="105" y="45" font-size="12" fill="blue">(100,50)</text>
<circle cx="200" cy="100" r="3" fill="green" />
<text x="205" y="95" font-size="12" fill="green">(200,100)</text>
</svg>
</div>viewBox是SVG中的重要概念,用于定义SVG的可视区域:
<!-- viewBox属性演示 -->
<div class="viewbox-demo">
<h4>viewBox属性演示</h4>
<div class="viewbox-examples">
<div class="viewbox-example">
<h5>原始尺寸</h5>
<svg width="150" height="100" viewBox="0 0 150 100">
<rect x="10" y="10" width="130" height="80" fill="lightcoral" stroke="darkred" stroke-width="2" />
<text x="75" y="55" text-anchor="middle" font-size="12">viewBox="0 0 150 100"</text>
</svg>
</div>
<div class="viewbox-example">
<h5>缩放视图</h5>
<svg width="150" height="100" viewBox="0 0 75 50">
<rect x="10" y="10" width="130" height="80" fill="lightgreen" stroke="darkgreen" stroke-width="2" />
<text x="75" y="55" text-anchor="middle" font-size="12">viewBox="0 0 75 50"</text>
</svg>
</div>
<div class="viewbox-example">
<h5>裁剪视图</h5>
<svg width="150" height="100" viewBox="25 25 100 50">
<rect x="10" y="10" width="130" height="80" fill="lightblue" stroke="darkblue" stroke-width="2" />
<text x="75" y="55" text-anchor="middle" font-size="12">viewBox="25 25 100 50"</text>
</svg>
</div>
</div>
</div>SVG提供了多种容器元素来组织图形内容:
<!-- SVG容器元素 -->
<svg width="350" height="250" viewBox="0 0 350 250">
<!-- 分组元素 -->
<g id="shapes-group" transform="translate(10,10)">
<rect x="0" y="0" width="80" height="60" fill="yellow" />
<circle cx="40" cy="30" r="20" fill="orange" />
<text x="40" y="35" text-anchor="middle" font-size="10">分组</text>
</g>
<!-- 定义元素 -->
<defs>
<linearGradient id="blueGradient" x1="0%" y1="0%" x2="100%" y2="100%">
<stop offset="0%" style="stop-color:lightblue;stop-opacity:1" />
<stop offset="100%" style="stop-color:darkblue;stop-opacity:1" />
</linearGradient>
</defs>
<!-- 使用定义的渐变 -->
<rect x="120" y="10" width="80" height="60" fill="url(#blueGradient)" />
<text x="160" y="45" text-anchor="middle" font-size="12" fill="white">渐变</text>
<!-- 符号元素 -->
<symbol id="star" viewBox="0 0 20 20">
<polygon points="10,1 13,7 19,7 14,12 16,18 10,15 4,18 6,12 1,7 7,7" fill="gold" />
</symbol>
<!-- 使用符号 -->
<use href="#star" x="230" y="10" width="30" height="30" />
<text x="245" y="55" text-anchor="middle" font-size="12">符号</text>
</svg>完整的SVG文档具有清晰的结构:
<!-- 完整的SVG文档结构 -->
<svg width="400" height="300"
viewBox="0 0 400 300"
xmlns="http://www.w3.org/2000/svg"
role="img"
aria-labelledby="svg-title"
aria-describedby="svg-desc">
<!-- 标题和描述 -->
<title id="svg-title">SVG文档结构示例</title>
<desc id="svg-desc">这是一个展示SVG文档结构的示例图形</desc>
<!-- 定义部分 -->
<defs>
<style>
.header-text { font-size: 18px; font-weight: bold; fill: #333; }
.content-text { font-size: 14px; fill: #666; }
</style>
</defs>
<!-- 主要内容 -->
<rect x="10" y="10" width="380" height="280" fill="none" stroke="#999" stroke-width="2" />
<text x="200" y="40" text-anchor="middle" class="header-text">SVG文档结构</text>
<g id="content-area">
<text x="30" y="80" class="content-text">1. 声明和命名空间</text>
<text x="30" y="110" class="content-text">2. 标题和描述</text>
<text x="30" y="140" class="content-text">3. 定义部分(defs)</text>
<text x="30" y="170" class="content-text">4. 主要图形内容</text>
<text x="30" y="200" class="content-text">5. 样式和效果</text>
</g>
</svg>SVG应该包含适当的可访问性标记:
<!-- 带有可访问性的SVG -->
<svg width="300" height="200"
viewBox="0 0 300 200"
role="img"
aria-labelledby="accessible-title"
aria-describedby="accessible-desc">
<title id="accessible-title">公司销售数据图表</title>
<desc id="accessible-desc">
这是一个柱状图,显示了公司2023年各季度的销售数据。
第一季度销售额为100万,第二季度为150万,第三季度为120万,第四季度为180万。
</desc>
<!-- 图表内容 -->
<g id="chart-content">
<rect x="50" y="120" width="40" height="60" fill="blue" />
<text x="70" y="195" text-anchor="middle" font-size="12">Q1</text>
<rect x="110" y="80" width="40" height="100" fill="green" />
<text x="130" y="195" text-anchor="middle" font-size="12">Q2</text>
<rect x="170" y="100" width="40" height="80" fill="orange" />
<text x="190" y="195" text-anchor="middle" font-size="12">Q3</text>
<rect x="230" y="60" width="40" height="120" fill="red" />
<text x="250" y="195" text-anchor="middle" font-size="12">Q4</text>
</g>
</svg><!-- 提供详细文本替代的SVG -->
<div class="svg-with-alternative">
<svg width="250" height="150" viewBox="0 0 250 150"
role="img" aria-label="流程图示例">
<rect x="20" y="40" width="80" height="40" fill="lightblue" stroke="blue" stroke-width="2" />
<text x="60" y="65" text-anchor="middle" font-size="12">开始</text>
<line x1="100" y1="60" x2="130" y2="60" stroke="black" stroke-width="2" marker-end="url(#arrowhead)" />
<rect x="130" y="40" width="80" height="40" fill="lightgreen" stroke="green" stroke-width="2" />
<text x="170" y="65" text-anchor="middle" font-size="12">处理</text>
<defs>
<marker id="arrowhead" markerWidth="10" markerHeight="7" refX="9" refY="3.5" orient="auto">
<polygon points="0 0, 10 3.5, 0 7" fill="black" />
</marker>
</defs>
</svg>
<!-- 文本替代内容 -->
<div class="text-alternative">
<h4>流程图文本描述</h4>
<p>这是一个简单的流程图,包含两个步骤:</p>
<ol>
<li>开始:流程的起始点</li>
<li>处理:执行主要处理逻辑</li>
</ol>
<p>两个步骤之间有箭头连接,表示执行顺序。</p>
</div>
</div>A: SVG适合简单图形、图标、Logo等需要缩放的场景;Canvas适合复杂动画、游戏、图像处理等需要像素级控制的场景。
A: viewBox定义了SVG的可视窗口,格式为"x y width height",可以实现图形的缩放、裁剪和定位效果。
A: 应该添加title和desc元素,使用适当的ARIA属性,为复杂图形提供文本替代描述。
A: 是的,SVG元素可以使用CSS样式,包括填充、描边、字体等属性,还可以使用CSS动画和过渡效果。
A: 可以使用img、object、embed标签引用外部SVG文件,或者使用CSS的background-image属性。
下一节预览:下一节我们将学习第8章第2节-SVG基本图形,重点介绍SVG中各种基本图形元素的语法和使用方法。