Canvas图形绘制

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

Canvas图形绘制
文章目录

o
o

















Canvas图形绘制
矩形绘制
•rect(x,y,w,h) 没有独立路径
•strokeRect(x,y,w,h) 有独立路径,不影响别的绘制•fillRect(x,y,w,h) 有独立路径,不影响别的绘制
•clearRect(x,y,w,h) 擦除矩形区域
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas>
<script>
var myCanvas = document.querySelector('canvas'); var ctx = myCanvas.getContext('2d');
/*绘制矩形路径不是独立路径*/
ctx.rect(100,100,100,100);
ctx.fillStyle = 'green';
ctx.stroke();
ctx.fill();
/*绘制矩形有自己的独立路径*/
ctx.fillStyle = 'red';
ctx.strokeRect(200,200,100,100);
ctx.fillStyle = 'skyblue';
ctx.fillRect(300,300,100,100);
/*清除矩形的内容*/
// ctx.clearRect(0,0,ctx.canvas.width,ctx.canvas.height);
</script>
</body>
</html> createLinearGradient()方法绘制渐变颜色矩形
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8"> <title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
}
/* .linearGradient{ width: 400px;
height: 100px;
background-image: linear-gradient(to right,pink,blue);
}*/
</style>
</head>
<body>
<div class="linearGradient"></div>
<canvas width="600" height="400"></canvas>
<script>
var myCanvas = document.querySelector('canvas');
var ctx = myCanvas.getContext('2d');
/*fillStyle 'pink' '#000' 'rgb()' 'rgba()' */
/*也可以使用一个渐变的方案了填充矩形*/
/*创建一个渐变的方案*/
/*渐变是由长度的*/
/*x0y0 起始点 x1y1 结束点确定长度和方向*/
var linearGradient = ctx.createLinearGradient(100,100,500,400);
linearGradient.addColorStop(0,'pink');
//linearGradient.addColorStop(0.5,'red');
linearGradient.addColorStop(1,'blue');
ctx.fillStyle = linearGradient;
ctx.fillRect(100,100,400,100);
/*pink---->blue*/
/*回想线性渐变---->要素方向起始颜色结束颜色 */
/*通过两个点的坐标可以控制渐变方向*/
</script>
</body>
</html>
圆弧绘制
弧度概念
这就和数学中的概念知识是一样的。

1.弧度:是一种长度的描述单位
2.一个弧度怎么去描述一个圆有多少个弧度2 * π
3.一弧度有多长一个弧度一个半径的长度
名词:
•角度:一个圆是360度
•半径:已一个点为中心多长为放射半径
•周长:2 * π * r
最终的结论:一个角度等于多少弧度π/180
用三角函数体验曲线的绘制
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas> <script>
var myCanvas = document.querySelector('canvas'); var ctx = myCanvas.getContext('2d');
/*1.体验曲线的绘制*/
/*2.线是由点构成的*/
/*3.曲线可以由数学公式得来*/
/*公式:y = x/2 */
/*公式:y = (x + 2) ^2 */
/*公式:y = sin(x) */
for(var i = 1 ; i < 600 ; i ++){
var x = i;
//var y = x/2;
//var y = Math.pow(x/10-30,2);
var y = 50*Math.sin(x/10) + 100;
ctx.lineTo(x,y);
}
ctx.stroke();
</script>
</body>
</html>
arc() 方法画圆弧
arc(x,y,r,startAngle,endAngle,anticlockwise)
参数:
•x 圆心横坐标
•y 圆心纵坐标
•r 半径
•startAngle 开始角度
•endAngle 结束角度
•anticlockwise 是否逆时针方向绘制(默认false表示顺时针;true表示逆时针)
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas>
<script>
var myCanvas = document.querySelector('canvas');
var ctx = myCanvas.getContext('2d');
/*绘制圆弧*/
/*确定圆心坐标 x y*/
/*确定圆半径 r */
/*确定起始绘制的位置和结束绘制的位置确定弧的长度和位置startAngle endAngle 弧度*/
/*取得绘制的方向 direction 默认是顺时针 false 逆时针 true */
/*在中心位置画一个半径150px的圆弧左下角*/
var w = ctx.canvas.width;
var h = ctx.canvas.height;
ctx.arc(w/2,h/2,150,Math.PI/2,Math.PI,true);
ctx.stroke();
</script>
</body>
</html>
圆实例练习
绘制六种颜色等分的圆
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas>
<script>
var myCanvas = document.querySelector('canvas');
var ctx = myCanvas.getContext('2d');
var w = ctx.canvas.width;
var h = ctx.canvas.height;
/*分成几等分*/
var num = 360;
/*一份多少弧度*/
var angle = Math.PI * 2 / num;
/*原点坐标*/
var x0 = w / 2;
var y0 = h / 2;
/*获取随机颜色*/
var getRandomColor = function () {
var r = Math.floor(Math.random() * 256);
var g = Math.floor(Math.random() * 256); var b = Math.floor(Math.random() * 256); return 'rgb(' + r + ',' + g + ',' + b + ')';
}
/*上一次绘制的结束弧度等于当前次的起始弧度*/ //var startAngle = 0;
for (var i = 0; i < num; i++) {
var startAngle = i * angle;
var endAngle = (i + 1) * angle;
ctx.beginPath();
ctx.moveTo(x0, y0);
ctx.arc(x0, y0, 150, startAngle, endAngle);
/*随机颜色*/
ctx.fillStyle = getRandomColor(); ctx.fill();
}
</script>
</body>
</html>
绘制扇形
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas>
<script>
var myCanvas = document.querySelector('canvas');
var ctx = myCanvas.getContext('2d');
/*在中心位置画一个半径150px的圆弧右上角扇形边填充 */ var w = ctx.canvas.width;
var h = ctx.canvas.height;
/*把起点放到圆心位置*/
ctx.moveTo(w/2,h/2);
ctx.arc(w/2,h/2,150,0,-Math.PI/2,true);
/*闭合路径*/
//ctx.closePath();
ctx.fill();
</script>
</body>
</html>
绘制数据饼图
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas> <script>
var myCanvas = document.querySelector('canvas'); var ctx = myCanvas.getContext('2d');
/*1.根据37期的年龄分布绘制饼图*/
/*2.准备统计的数据*/
/*15-20岁 6个*/
/*20-25岁 30个*/
/*25-30岁 10个*/
/*30-35岁 8个*/
var data = [6, 30, 10, 8];
/*3.在饼图表示出来*/
/*4.需要把数据转出弧度*/
var angleList = [];
var total = 0;
data.forEach(function (item, i) {
total += item;
});
console.log(total);
/*第二是转换成弧度的时候就可以去绘制扇形减少一次遍历*/ data.forEach(function (item, i) {
var angle = Math.PI * 2 * (item/total);
angleList.push(angle);
});
console.log(angleList);
/*5.根据弧度绘制扇形*/
var w = ctx.canvas.width;
var h = ctx.canvas.height;
var x0 = w/2;
var y0 = h/2;
/*获取随机颜色*/
var getRandomColor = function () {
var r = Math.floor(Math.random() * 256);
var g = Math.floor(Math.random() * 256);
var b = Math.floor(Math.random() * 256);
return 'rgb(' + r + ',' + g + ',' + b + ')';
}
var startAngle = 0;
angleList.forEach(function (item,i) {
/*上一次绘制的结束弧度等于当前次的起始弧度*/
var endAngle = startAngle + item;
ctx.beginPath();
ctx.moveTo(x0,y0);
ctx.arc(x0,y0,150,startAngle,endAngle);
ctx.fillStyle = getRandomColor();
ctx.fill();
/*记录当前的结束位置作为下一次的起始位置*/
startAngle = endAngle;
});
</script>
</body>
</html>
绘制文本
•ctx.font = '微软雅黑’ 设置字体
•strokeT ext()
•fillText(text,x,y,maxWidth)
o text 要绘制的文本
o x,y 文本绘制的坐标(文本左下角)
o maxWidth 设置文本最大宽度,可选参数
•ctx.textAlign文本水平对齐方式,相对绘制坐标来说的o left
o center
o right
o start 默认
o end
•ctx.direction属性css(rtl ltr) start和end于此相关
o如果是ltr,start和left表现一致
o如果是rtl,start和right表现一致
•ctx.textBaseline 设置基线(垂直对齐方式)
o top 文本的基线处于文本的正上方,并且有一段距离
o middle 文本的基线处于文本的正中间
o bottom 文本的基线处于文本的证下方,并且有一段距离o hanging 文本的基线处于文本的正上方,并且和文本粘合o alphabetic 默认值,基线处于文本的下方,并且穿过文字o ideographic 和bottom相似,但是不一样•measureText() 获取文本宽度obj.width
案例:画布中心绘制文字
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
display: block;
margin: 100px auto;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas> <script>
var myCanvas = document.querySelector('canvas'); var ctx = myCanvas.getContext('2d');
/*1.在画布的中心绘制一段文字*/
/*2.申明一段文字*/
var str = '您吃饭中饭了吗';
/*3.确定画布的中心*/
var w = ctx.canvas.width;
var h = ctx.canvas.height;
/*4.画一个十字架在画布的中心*/
ctx.beginPath();
ctx.moveTo(0, h / 2 - 0.5);
ctx.lineTo(w, h / 2 - 0.5);
ctx.moveTo(w / 2 - 0.5, 0);
ctx.lineTo(w / 2 - 0.5, h);
ctx.strokeStyle = '#eee';
ctx.stroke();
/*5.绘制文本*/
ctx.beginPath();
ctx.strokeStyle = '#000';
var x0 = w/2;
var y0 = h/2;
/*注意:起点位置在文字的左下角*/
/*有文本的属性尺寸字体左右对齐方式垂直对齐的方式*/
ctx.font = '40px Microsoft YaHei';
/*左右对齐方式 (center left right start end) 基准起始坐标*/
ctx.textAlign = 'center';
/*垂直对齐的方式基线 baseline(top,bottom,middle) 基准起始坐标*/
ctx.textBaseline = 'middle';
//ctx.direction = 'rtl';
//ctx.strokeText(str,x0,y0);
ctx.fillText(str,x0,y0);
/*6.画一个下划线和文字一样长*/
ctx.beginPath();
/*获取文本的宽度*/
console.log(ctx.measureText(str));
var width = ctx.measureText(str).width;
ctx.moveTo(x0-width/2,y0 + 20);
ctx.lineTo(x0+width/2,y0 + 20);
ctx.stroke();
</script>
</body>
</html>
圆与文本综合案例:数据饼状图
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
canvas {
border: 1px solid #ccc;
display: block;
margin: 100px auto;
}
</style>
</head>
<body>
<canvas width="600" height="400"></canvas>
<script>
/*var myCanvas = document.querySelector('canvas'); var ctx = myCanvas.getContext('2d');*/
/*1.绘制饼状态图*/
/*1.1 根据数据绘制一个饼图*/
/*1.2 绘制标题从扇形的弧中心伸出一条线在画一条横线在横线的上面写上文字标题*/
/*1.3 在画布的左上角绘制说明一个和扇形一样颜色的矩形旁边就是文字说明*/
var PieChart = function (ctx) {
/*绘制工具*/
this.ctx = ctx || document.querySelector('canvas').getContext('2d');
/*绘制饼图的中心*/
this.w = this.ctx.canvas.width;
this.h = this.ctx.canvas.height;
/*圆心*/
this.x0 = this.w / 2 + 60;
this.y0 = this.h / 2;
/*半径*/
this.radius = 150;
/*伸出去的线的长度*/
this.outLine = 20;
/*说明的矩形大小*/
this.rectW = 30;
this.rectH = 16;
this.space = 20;
}
PieChart.prototype.init = function (data) {
/*1.准备数据*/
this.drawPie(data);
};
PieChart.prototype.drawPie = function (data) {
var that = this;
/*1.转化弧度*/
var angleList = this.transformAngle(data);
/*2.绘制饼图*/
var startAngle = 0;
angleList.forEach(function (item, i) {
/*当前的结束弧度要等于下一次的起始弧度*/
var endAngle = startAngle + item.angle;
that.ctx.beginPath();
that.ctx.moveTo(that.x0, that.y0);
that.ctx.arc(that.x0, that.y0, that.radius, startAngle, endAngle);
var color = that.ctx.fillStyle = that.getRandomColor();
that.ctx.fill();
/*下一次要使用当前的这一次的结束角度*/
/*绘制标题*/
that.drawTitle(startAngle, item.angle, color , item.title);
/*绘制说明*/
that.drawDesc(i,item.title);
startAngle = endAngle;
});
};
PieChart.prototype.drawTitle = function (startAngle, angle ,color , title) {
/*1.确定伸出去的线通过圆心点通过伸出去的点确定这个线*/ /*2.确定伸出去的点需要确定伸出去的线的长度*/
/*3.固定伸出去的线的长度*/
/*4.计算这个点的坐标*/
/*5.需要根据角度和斜边的长度*/
/*5.1 使用弧度当前扇形的起始弧度 + 对应的弧度的一半 */
/*5.2 半径+伸出去的长度 */
/*5.3 outX = x0 + cos(angle) * ( r + outLine)*/
/*5.3 outY = y0 + sin(angle) * ( r + outLine)*/
/*斜边*/
var edge = this.radius + this.outLine;
/*x轴方向的直角边*/
var edgeX = Math.cos(startAngle + angle / 2) * edge;
/*y轴方向的直角边*/
var edgeY = Math.sin(startAngle + angle / 2) * edge;
/*计算出去的点坐标*/
var outX = this.x0 + edgeX;
var outY = this.y0 + edgeY;
this.ctx.beginPath();
this.ctx.moveTo(this.x0, this.y0);
this.ctx.lineTo(outX, outY);
this.ctx.strokeStyle = color;
/*画文字和下划线*/
/*线的方向怎么判断伸出去的点在X0的左边线的方向就是左边*/
/*线的方向怎么判断伸出去的点在X0的右边线的方向就是右边*/
/*结束的点坐标和文字大小*/
this.ctx.font = '14px Microsoft YaHei';
var textWidth = this.ctx.measureText(title).width ;
if(outX > this.x0){
/*右*/
this.ctx.lineTo(outX + textWidth,outY);
this.ctx.textAlign = 'left';
}else{
/*左*/
this.ctx.lineTo(outX - textWidth,outY);
this.ctx.textAlign = 'right';
}
this.ctx.stroke();
this.ctx.textBaseline = 'bottom';
this.ctx.fillText(title,outX,outY);
};
PieChart.prototype.drawDesc = function (index,title) {
/*绘制说明*/
/*矩形的大小*/
/*距离上和左边的间距*/
/*矩形之间的间距*/
this.ctx.fillRect(this.space,this.space + index * (this.rectH + 10),this.rectW,this.rectH);
/*绘制文字*/
this.ctx.beginPath();
this.ctx.textAlign = 'left';
this.ctx.textBaseline = 'top';
this.ctx.font = '12px Microsoft YaHei';
this.ctx.fillText(title,this.space + this.rectW + 10 , this.space + index * (this.rectH + 10));
};
PieChart.prototype.transformAngle = function (data) {
/*返回的数据内容包含弧度的*/
var total = 0;
data.forEach(function (item, i) {
total += item.num;
});
/*计算弧度并且追加到当前的对象内容*/
data.forEach(function (item, i) {
var angle = item.num / total * Math.PI * 2;
item.angle = angle;
});
return data;
};
PieChart.prototype.getRandomColor = function () { var r = Math.floor(Math.random() * 256);
var g = Math.floor(Math.random() * 256);
var b = Math.floor(Math.random() * 256);
return 'rgb(' + r + ',' + g + ',' + b + ')';
};
var data = [
{
title: '15-20岁',
num: 6
},
{
title: '20-25岁',
num: 30
},
{
title: '25-30岁',
num: 10
},
{
title: '30以上',
num: 8
}
];
var pieChart = new PieChart(); pieChart.init(data);
</script>
</body>
</html>。

相关文档
最新文档