Canvas
很早就知道这个东西了,一直很想学习,趁着清明小假期,终于有时间来学一下它了!
1.1 初识
注意canvas 的 width 和 height 不要用 css 来设定,如果用 css 样式来设置,会变形和失真
代码语言:javascript复制<canvas width="500" height="500">
当前浏览器版本不支持,请升级浏览器
</canvas>
ie 678不支持
1.1.1 基本使用
代码语言:javascript复制<script>
//获取画布
var canvas = document.getElementById('myCanvas');
//得到画布的上下文
var ctx = canvas.getContext('2d');
//设置颜色
ctx.fillStyle = 'red';
//绘制图形
ctx.fillRect(100,100,200,50);//前两个表示,x,y的坐标,后两个是宽高
</script>
一定要先设置颜色,再绘制图形
1.1.2 canvas 像素化
用canvas绘制一个图形,一旦绘制成功,canvas就像素化他们。canvas没有能力,从画布上再次得到这个图形,也就是不能修改画布内容,这也是轻量化的原因
实现动画效果需要经历
- 清屏
- 更新
- 渲染
也就是需要重新绘制
1.1.3 canvas 第一个动画
实现一个盒子滑动的效果
代码语言:javascript复制<script>
var canvas = document.getElementById('myCanvas');
var ctx = canvas.getContext('2d');
ctx.fillStyle = 'skyblue';
//信号量
var left = 0;
//动画过程
setInterval(function() {
//清屏
ctx.clearRect(0,0,500,500);
//距离画布左侧距离增加
left ;
//重新绘制
ctx.fillRect(left,100,100,100);
})
</script>
每一次的更新重绘的画面叫做一帧
1.1.4 面向对象思维实现canvas 动画
代码语言:javascript复制用面向对象的方式来维持canvas需要的属性和状态
<script>
var canvas = document.getElementById('myCanvas');
var ctx = canvas.getContext('2d');
//构造函数
function Rect(x, y, w, h, color) {
this.x = x;
this.y = y;
this.w = w;
this.h = h;
this.color = color;
}
//给函数原型添加方法
Rect.prototype.update = function () {
this.x ;
}
Rect.prototype.render = function () {
ctx.fillStyle = this.color;
ctx.fillRect(this.x, this.y, this.w, this.h);
}
//实例化
var r1 = new Rect(100, 100, 50, 50, 'skyblue');
var r2 = new Rect(100, 200, 50, 50, 'pink');
setInterval(function () {
//清屏
ctx.clearRect(0, 0, canvas.width, canvas.height);
r1.update(); //更新
r1.render(); //重绘
r2.update(); //更新
r2.render(); //重绘
})
</script>
2.1 绘制图形
2.1.1 填充矩形
代码语言:javascript复制//设置颜色
ctx.fillStyle = 'red';
//绘制图形
ctx.fillRect(100,100,200,50); //前两个表示,x,y的坐标,后两个是宽高
2.1.2 绘制边框
代码语言:javascript复制ctx.strokeStyle = 'red'; //边框颜色
ctx.strokeRect(300,100,100,100); //边框大小
2.2 绘制路径
- 需要设置路径的起点
- 使用绘制命令画出路径
- 封闭路径
- 填充或者绘制已经封闭路径的形状
<script>
var canvas = document.getElementById('myCanvas');
var ctx = canvas.getContext('2d');
//创建一个路径
ctx.beginPath();
//移动位置点 起始点
ctx.moveTo(100,100);
// 描述行进路径
ctx.lineTo(200,200);
ctx.lineTo(400,180);
// 封闭路径
ctx.closePath();
// 绘制图形
ctx.strokeStyle = 'red';
ctx.stroke();//画线
</script>
stroke()
通过线条来绘制图形轮廓。strokeRect是绘制矩形,要传参,描边fill()
通过填充路径的内容区域生成实心的图形。填充
在绘制路径的时候可以不关闭路径(不设置closePath()),这个时候会实现自封闭现象(只针对fill功能)
2.3 绘制圆弧
代码语言:javascript复制arc(x, y, radius, startAngle, endAngle, anticlockwise) 画一个以(x,y)为圆心的以radius为半径的圆弧(圆),从startAngle开始到endAngle结束,按照anticlockwise给定的方向(默认为顺时针)来生成
<script>
var canvas = document.getElementById('myCanvas');
var ctx = canvas.getContext('2d');
//创建一个路径
ctx.beginPath();
//描绘路径
ctx.arc(200, 200, 50, 0, 2 * Math.PI, false);//默认为false,顺时针
//画路径
ctx.stroke();
</script>
这里的意思是顺时针绘制一个圆心坐标(200,200)半径为50,弧度为2PI的圆
2.4 炫彩小球案例
通过给原型添加方法来给实例对象添加方法,使得个所有实例化构造出来的对象出生就带上这些方法
实现步骤
- 创建小球
- 给小球添加随机颜色,随机半径
- 鼠标移动实例化小球,新增小球
- 通过调用给原型新增的方法,来实现小球的动画效果
- 通过定时器不断地更新画布
2.5 透明度
代码语言:javascript复制ctx.globalAlpha = 0.4;
2.6 线性
代码语言:javascript复制利用lineWidth设置线的粗细,属性值必须是数字,默认是1.0,没有单位
ctx.lineWidth = 10;//设置线的粗细
lineCap
属性决定了线段末端的属性,3个值butt,round,square
lineJoin
属性决定了图形中两段链接处所显示的样子round,bevel(平角),miter(默认)
setLineDash
定义虚线样式,接收一个数组
ctx.setLineDash([10, 20]);
第一个参数是虚线的宽度,第二个参数是两个虚线之间的距离,以此类推,即虚线的交替状态
代码语言:javascript复制lineDashOffset可以来设置虚线的起始偏移量
lineDashOffset = 10;//虚线起始偏移亮,就是拿个虚线小格移多少
2.7 文本
代码语言:javascript复制var canvas = document.getElementById('myCanvas');
var ctx = canvas.getContext('2d');
ctx.font = '30px 宋体';
ctx.textAlign = 'center';//对齐方式基于fillText的x值
ctx.fillText('我是ljc', 100, 100);//文本内容和文本的位置
2.8 渐变
线性渐变
代码语言:javascript复制ctx.createLinearGradient(x0, y0, x1, y1);//前两个参数是起始位置,后两个是结束位置
代码语言:javascript复制var linear = ctx.createLinearGradient(10,10,200,100);//渐变颜色
linear.addColorStop(0,'red');
linear.addColorStop(0.5,'blue');
linear.addColorStop(1,'skyblue');//渐变位置和颜色
ctx.fillStyle = linear;//给颜色
ctx.fillRect(10,10,200,100);
径向渐变
代码语言:javascript复制ctx.createRadialGradient(x0, y0, r0, x1, y1, r1);//开始圆形的x,y,r和结束的x,y,r
用法和线性渐变相同
2.9 阴影
设置文字阴影效果
代码语言:javascript复制ctx.shadowOffsetX = 10;//阴影左右偏离的距离
ctx.shadowOffsetY = 10;//阴影上下偏离的距离
ctx.shadowBlur = 2;//模糊值
ctx.shadowColor = 'black';//阴影颜色
ctx.font = '30px 宋体';
ctx.textAlign = 'center';
ctx.fillText('我是ljc', 100, 100);//文本内容和文本的位置
3.1 使用图片
代码语言:javascript复制var canvas = document.getElementById('myCanvas');
var ctx = canvas.getContext('2d');
var image = new Image();//产生image元素
image.src = 'imgs/1.jpg';//图片路径
//必须在onload之后再绘制图片,否则不会渲染
image.onload = function() {
ctx.drawImage(image,100,100,200,200);//加载得图片和加载的位置和图片尺寸
}
关于参数的问题(不包含image)
- 2个参数,表示绘制图片的位置
- 4个参数,前两个参数表示绘制的位置,后面2个表示图片的尺寸
- 8个参数,前2个参数描述切片的位置,接下来2个是切片的尺寸,在接下来2个是切下来的图片放到什么位置,最后2个是图片的大小
ctx.drawImage(image,0,0,200,200,0,50,90,90);
这个意思是在(0,0)的位置用一个200 * 200的切片从图片上切下一块图片,放到(0,50)的位置,最后把图片大小缩放为90*90
4.1 资源管理器
代码就不放了
5.1 变形
canvas是可以进行变形的,变形的不是元素,而是整个画布的渲染区域在变形
**save() **保存画布的所有状态 restore() 恢复 canvas状态的
save起到一个存档的作用,有点像我们打游戏的时候的存档,当我们想重新回到那个位置时,就可以读档也就是这里的restore()
在每次进行变形之前都要先进行存档,再绘画,这样不影响后面的操作
5.1.1 translate平移
代码语言:javascript复制ctx.translate(50, 50);
5.1.2 rotate 旋转
代码语言:javascript复制ctx.rotate(deg)
5.1.3 scale 缩放
这里的缩放和css3的不同,需要传2个参数,代表x,y的缩放比例
代码语言:javascript复制ctx.scale(0.5, 0.5)
5.1.4 混合写法
transform(a, b, c, d, e, f)
- a 水平方向的缩放
- b 竖直方向的倾斜偏移
- c 水平方向的倾斜偏移
- d 竖直方向的缩放
- e 水平方向的移动
- f 竖直方向的移动
ctx.transform(0.5, 1.1, 1.1, 0.5, 100, 100)
6.1 合成
这个就相当于蒙版状态,就是用来设置如何压盖,如何显示
代码语言:javascript复制ctx.globalCompositeOperation = "destination-over"
属性 | 说明 |
---|---|
source-over | 这个是默认值,新图形绘制于已有图形的顶部 |
destination-over | 新图形绘制于已有内容的后面 |
source-in | 在新图形以及已有内容重叠的地方,新图形才绘制。所有其他内容成为透明。 |
source-out | 只有在和已有图形不重叠的地方才绘制新图形 |
source-atop | 只有在新图形和已有内容重叠的地方才绘制新图形 |
destination-in | 在新图形以及已有画布重叠的地方,已有内容都保留。所有其他内容成为透明的 |
destination-out | 在已有内容和新图形不重叠的地方,已有内容保留。所有其他内容成为透明 |
destination-atop | 已有的内容只有在它和新的图形重叠的地方保留。新图形绘制于内容之后 |
lighter | 在图形重叠的地方,颜色由两种颜色值的加值来决定 |