HTML5之svg
矢量图,缩放不变形。
1. 绘制基础
1.1标签绘制
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg基础</title>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" width="800" height="800">
<rect x="10" y="10" width="50" height="50" rx="5" ry="5" fill="#000"/>
<circle cx="35" cy="100" r="20" />
<ellipse cx="35" cy="160" rx="30" ry="20" />
<line x1="10" y1="200" x2="200" y2="200"
style="stroke:rgb(99,99,99);stroke-width:5" />
<polyline points="10,250 500,250 80,300" style="stroke-width:1" />
</svg>
</body>
</html>
1.2 js绘制
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>demo</title>
</head>
<body>
<div id="canvas"></div>
<script>
var SVG_NS = 'http://www.w3.org/2000/svg';
var canvas = document.getElementById('canvas');
function createSVG(){
var svg = document.createElementNS(SVG_NS, 'svg');
svg.setAttribute('width', '800');
svg.setAttribute('height', '800');
var circle = document.createElementNS(SVG_NS, 'circle');
circle.setAttribute('cx', '35');
circle.setAttribute('cy', '50');
circle.setAttribute('r', '20');
circle.setAttribute('stroke-width', '5');
svg.appendChild(circle);
canvas.appendChild(svg);
return svg;
};
createSVG()
</script>
</body>
</html>
1.3 path绘制
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg</title>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" width="800" height="800">
<!-- 简单点线命令 -->
<!-- <path d="M10 10 H 90 V 90 H 10 L 10 10 " /> -->
<!-- 三次贝塞尔曲线需要定义一个点和两个控制点 -->
<!-- <path d="M10 110 C 0 140, 60 140, 50 110" stroke="black" fill="transparent"/> -->
<!-- 三次贝塞尔曲线简写 -->
<!-- <path d="M10 80 C 40 10, 65 10, 95 80 S 150 150, 180 80" stroke="black" fill="transparent"/> -->
<!--二次贝塞尔曲线只需要一个控制点,用来确定起点和终点的曲线斜率-->
<!-- <path d="M10 80 Q 95 10 180 80" stroke="black" fill="transparent"/> -->
<!-- 二次贝塞尔曲线简写 -->
<!-- <path d="M10 80 Q 52.5 10, 95 80 T 180 80" stroke="black" fill="transparent"/> -->
<!-- 弧形 -->
<!-- x轴半径,y轴半径,旋转情况,弧线角度,弧线方向, -->
<path d="M10 315
L 110 215
A 30 50 0 0 1 162.55 162.45
L 172.55 152.45
A 30 50 -45 0 1 215.1 109.9
L 315 10" stroke="black" fill="green" stroke-width="2" fill-opacity="0.5"/>
</svg>
</body>
</html>
1.4 文本绘制
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg</title>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" width="800" height="800">
<text x="20" y="90" dx="10 20 20 60" dy="10" style="font-size: 50px;font-family:'Arial'">SVGA文本插入</text>
<path d="M30,0 V200,M0,100H200" stroke="red"></path>
</svg>
</body>
</html>
2.动画基础
2.1 直线动画
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg动画</title>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" width="10000" height="1000">
<rect x="100" y="100" width="100" height="100" fill="red">
<animate
id="goright"
attributeType="XML"
attributeName="x"
begin="0;goleft.end"
form="100"
to="500"
dur="2s"
fill="freeze"
></animate>
<animate
id="goleft"
attributeType="XML"
attributeName="x"
begin="goright.end"
form="500"
to="100"
dur="2s"
fill="freeze"
></animate>
</rect>
</svg>
</body>
</html>
2.2 弧线动画
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg动画</title>
</head>
<body>
<svg
xmlns="http://www.w3.org/2000/svg"
width="1000"
height="1000"
>
<rect x="200" y="0" width="100" height="100" fill="red">
<animateTransform
id="rotate"
attributeName="transform"
attributeType="XML"
type="rotate"
form="0"
to="60"
dur="2s"
fill="freeze"
></animate>
</rect>
</svg>
</body>
</html>
2.3 轨迹动画
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg动画</title>
</head>
<body>
<svg
xmlns="http://www.w3.org/2000/svg"
width="10000"
height="1000"
viewBox="-400 -400 800 800"
>
<rect
x="-25"
y="-25"
width="100"
height="100"
fill="rgba(0,255,255,.6)"
>
<!-- <animateMotion
path="M 0 0 L 100 100 A 200 200 0 1 0 0 -100"
dur="3s"
rotate="auto"
>
</animateMotion> -->
<animateMotion
dur="3s"
rotate="auto"
>
<mpath xlink:href="#motion-path"></mpath>
</animateMotion>
</rect>
<path
id="motion-path"
d="M 0 0 L 100 100 A 200 200 0 1 0 0 -100"
stroke="red"
fill="none"
></path>
</svg>
</body>
</html>
2.4 文本动画
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg</title>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" width="1000" height="1000">
<defs>
<pattern id="grid" x="0" y="0" width="20" height="20" patternUnits="userSpaceOnUse">
<path stroke="#F0F0F0" fill="none" d="M0,0H20V20"></path>
</pattern>
</defs>
<rect width="1200" height="1000" fill="url(#grid)"></rect>
<text id="sintext" x="100" y="160" style="font-size: 14px;font-family:'Arial'">ABCDEFGHIJKLMNOPQRSTUVWXYZ</text>
<path d="M100,0 V200M0,100H200" transform="translate(0,60)" stroke="red"></path>
</svg>
<script>
var n = 26;
var x = [];
var y = null;
var i = n;
var s = 100;
var w = 0.02;
var t = 0;
while(i--) x.push(10);
function arrange(t){
y = [];
var ly = 0, cy;
for(i=0;i<n;++i){
cy = -s*Math.sin(w*i*20+t);
y.push(cy-ly);
ly = cy;
}
}
//渲染函数
function render(){
sintext.setAttribute('dx',x.join(' '));
sintext.setAttribute('dy',y.join(' '));
}
//动画函数
function frame(){
t+=0.02;
arrange(t);
render();
requestAnimationFrame(frame);
};
frame()
</script>
</body>
</html>
2.5 动画综合练习
vector.js
(function(){
function Vector(x,y){
this.x = x || 0;
this.y = y || 0;
}
Vector.prototype = {
constructor:Vector,
square:function(){
return this.x * this.x + this.y * this.y;
},
length:function(){
return Math.sqrt(this.square());
},
add:function(q){
return new Vector(this.x + q.x,this.y+q.y);
},
minus:function(q){
return new Vector(this.x - q.x,this.y-q.y);
},
multipy:function(scale){
return new Vector(this.x*scale,this.y*scale);
},
normalize:function(length){
if(length === undefined){
length = 1;
}
return this.multipy(length / this.length());
}
};
Vector.fromPoints = function(p1,p2){
return new Vector(p2.x - p1.x, p2.y - p1.y);
};
window.Vector = Vector;
})();
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>svg动画</title>
<style>
html,body,svg{
margin:0;
padding:0;
width: 100%;
height:100%;
}
</style>
</head>
<body>
<svg
width="10000"
height="1000"
viewBox="-400 -400 800 800"
>
<path
id="links"
stroke="gray"
fill="none"
></path>
</svg>
<script src="vector.js"></script>
<script>
var points = 'a,b,c'.split(',').map(function(name,index,arr){
return {
name:name,
color:'hsl('+ (360*index/arr.length) + ',100%,60%)'
};
});
var relation = 300;
var svg = document.querySelector('svg');
var k = 0.05;
var Vector = window.Vector;
function random(min,max){
return Math.round(min +(max - min) *Math.random());
};
points.forEach(function(point){
var circle = document.createElementNS('http://www.w3.org/2000/svg','circle');
var x = random(-400,400);
var y = random(-400,400);
circle.setAttribute('cx',x);
circle.setAttribute('cy',y);
circle.setAttribute('r',10);
circle.setAttribute('fill',point.color);
svg.appendChild(circle);
point.circle = circle;
point.s = new Vector(x,y);
point.v = new Vector();
point.a = new Vector();
});
var lastFrameTime = +new Date();
function update(){
var frameTime = +new Date();
var t = frameTime - lastFrameTime;
t/=200;
//点位置更新
points.forEach(function(pa){
var f = new Vector();
//计算合力
points.forEach(function(pb){
if(pa == pb) return;
var x = Vector.fromPoints(pa.s,pb.s);
var delta = x.length() -relation;
//f = k * x
f = f.add(x.normalize(delta * k));
});
pa.a = f;
pa.v = pa.v.add(pa.a.multipy(t)).multipy(0.98);
pa.s = pa.s.add(pa.v.multipy(t));
pa.circle.setAttribute('cx',pa.s.x);
pa.circle.setAttribute('cy',pa.s.y);
});
//连线更新
var linkPath = [];
points.forEach(function(pa){
var sa = pa.s;
points.forEach(function(pb){
if(pa == pb) return;
var sb = pb.s;
linkPath = linkPath.concat([
'M',sa.x,sa.y,
'L',sb.x,sb.y
]);
});
});
document.getElementById('links').setAttribute('d',linkPath.join(' '))
lastFrameTime = frameTime;
window.requestAnimationFrame(update);
};
window.requestAnimationFrame(update);
</script>
</body>
</html>
3.图案动画
<!DOCTYPE html>
<html>
<head>
<meta name="description" content="满天星与灯塔">
<meta charset="utf-8">
<title>图案处理/title>
<style>
html, body {
margin: 0;
padding: 0;
width: 100%;
height: 100%;
background: #001122;
line-height: 0;
font-size: 0;
}
</style>
</head>
<body>
<svg id='svg' width="100%" height="100%" viewBox="-400 -300 800 600" preserveAspectRatio="xMidYMid slice">
<defs>
<polygon id="star" points="0 -10 2 -2 10 0 2 2 0 10 -2 2 -10 0 -2 -2" fill="white"></polygon>
</defs>
<g id="star-group"></g>
<g id="moon-group">
<mask id="moon-mask">
<circle cx="-250" cy="-150" r="100" fill="white"></circle>
<circle cx="-200" cy="-200" r="100" fill="black"></circle>
</mask>
<circle cx="-250" cy="-150" r="100" fill="white" mask="url(#moon-mask)"></circle>
</g>
<g id="light-tower" transform="translate(250,0)">
<defs>
<linearGradient id="tower" x1="0" y1="0" x2="1" y2="0">
<stop offset="0" stop-color="#999"></stop>
<stop offset="1" stop-color="#333"></stop>
</linearGradient>
<radialGradient id="light" cx="0.5" cy="0.5" r="0.5">
<stop offset="0" stop-color="rgba(255,255,255,.8)"></stop>
<stop offset="1" stop-color="rgba(255,255,255,0)"></stop>
</radialGradient>
<clipPath id="light-mask">
<polygon points="0 0 -400 -15 -400 15" fill="rgba(255,0,0,0.5)">
<animateTransform attributeName="transform" attributeType="XML" type="rotate" from="0" to="360" dur="7s" repeatCount="indefinite"></animateTransform>
</polygon>
<circle cx="0" cy="0" r="2"></circle>
</clipPath>
</defs>
<polygon points="0 0 5 50 -5 50" fill="url(#tower)"></polygon>
<ellipse cx="0" cy="0" rx="300" ry="100" fill="url(#light)" clip-path="url(#light-mask)"></ellipse>
</g>
</svg>
<script>
var paper = document.getElementById('svg');
var SVG_NS = 'http://www.w3.org/2000/svg';
var XLINK_NS = 'http://www.w3.org/1999/xlink';
renderStar();
function use(origin) {
var _use = document.createElementNS(SVG_NS, 'use');
_use.setAttributeNS(XLINK_NS, 'xlink:href', '#' + origin.id);
return _use;
}
function random (min, max) {
return min + (max - min) * Math.random();
}
function renderStar() {
var starRef = document.getElementById('star');
var starGroup = document.getElementById('star-group');
var starCount = 500;
while(starCount--){
star = use(starRef);
star.setAttribute('opacity', random(0.1, 0.4));
star.setAttribute('transform', 'translate(' + random(-400, 400) + ',' + random(-300, 50) + ')' + ' scale(' + random(0.1, 0.6) + ')');
starGroup.appendChild(star);
}
}
</script>
</body>
</html>
这篇是对慕、课、网svg教程的笔记,链接贴在下面,大家可以去看看:
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。