【H5】HTML5 Canvas 基础
HTML5 Canvas 基础
一、HTML5画布元素
1.1 Canvas 元素
注释:Internet Explorer 8 或更早的浏览器不支持
<canvas>
元素。
<canvas id="canvas" width="500" height="300">您的浏览器不支持画布!</canvas>
1.2 2D context
var context = canvas.getContext('2d');
1.3 WebGL context (3D)
var context = canvas.getContext('webgl');
二、颜色格式
// 字符串
context.fillStyle = 'red';
// 16进制
context.fillStyle = '#ff0000';
// 16进制简写
context.fillStyle = '#f00';
// RGB
context.fillStyle = 'rgb(255,0,0)';
// RGBA
context.fillStyle = 'rgba(255,0,0,1)';
三、图形
3.1 绘制方形
context.rect(x, y, width, height);
context.fill();
context.stroke();
3.2 填充区域
context.fillRect(x, y, width, height);
3.3 绘制方形的边框
context.strokeRect(x, y, width, height);
3.4 绘制圆形
context.arc(x, y, radius, 0, Math.PI * 2);
context.fill();
context.stroke();
四、路径
4.1 开始路径
context.beginPath();
4.2 画线
context.lineTo(x, y);
4.3 弧形
// x 圆的中心的 x 坐标。
// y 圆的中心的 y 坐标。
// r 圆的半径。
// sAngle 起始角,以弧度计。(弧的圆形的三点钟位置是 0 度)。
// eAngle 结束角,以弧度计。
// counterClockwise 可选。规定应该逆时针还是顺时针绘图。False = 顺时针,true = 逆时针。
context.arc(x, y, radius, sAngle, eArgle, counterClockwise);
4.4 二次曲线
context.quadraticCurveTo(cx, cy, x, y);
4.5 贝赛尔曲线
context.bezierCurveTo(cx1, cy1, cx2, cy2, x, y);
4.6 关闭路径
context.closePath();
五、图像
5.1 画图
var imageObj = new Image();
imageObj.onload = function () {
context.drawImage(imageObj, x, y);
}
imageObj.src = 'path/to/my/image.jpg';
5.2 指定尺寸画图
var imageObj = new Image();
imageObj.onload = function () {
context.drawImage(imageObj, x, y, width, height);
}
imageObj.src = 'path/to/my/image.jpg';
5.3 裁剪图片
var imageObj = new Image();
imageObj.onload = function () {
context.drawImage(imageObj, sx, sy, sw, sh, dx, dy, dw, dh);
}
imageObj.src = 'path/to/my/image.jpg';
六、文本
6.1 写文字
context.font = '40px Arial';
context.fillStyle = 'red';
context.fillText('Hello World!', x, y);
6.2 写镂空文字
context.font = '40px Arial';
context.fillStyle = 'red';
context.strokeText('Hello World!', x, y);
6.3 粗体
context.font = 'bold 40px Arial';
6.4. 斜体
context.font = 'italic 40px Arial';
6.5 对齐方式
context.textAlign = 'start|end|left|center|right';
6.6 文字基线
context.textBaseline = 'top|hanging|middle|alphabetic|ideographic|bottom';
6.7 获取文本宽度
var width = context.measureText('Hello world').width;
6.8 绘制文本并自动换行
// 寻找切换断点
findBreakPoint(text, width, context) {
let min = 0;
let max = text.length - 1;
while (min <= max) {
let middle = Math.floor((min + max) / 2);
let middleWidth = context.measureText(text.substr(0, middle)).width;
let oneCharWiderThanMiddleWidth = context.measureText(text.substr(0, middle + 1)).width;
if (middleWidth <= width && oneCharWiderThanMiddleWidth > width) {
return middle;
}
if (middleWidth < width) {
min = middle + 1;
} else {
max = middle - 1;
}
}
return -1;
}
// 文本自动换行,返回字符串数组
breakLinesForCanvas(context, text, width) {
let result = [];
let w = context.measureText(text).width
if (w <= width) return [context]
let breakPoint = 0;
while ((breakPoint = findBreakPoint(text, width, context)) !== -1) {
result.push(text.substr(0, breakPoint));
text = text.substr(breakPoint);
}
if (text) {
result.push(text);
}
return result;
}
// 绘制文本(自动换行)
drawText(context, text, x, y, width, height, lineHeight) {
var lines = breakLinesForCanvas(context, text, width);
if (lines.length > 1) {
var lh = lineHeight ? lineHeight : 15;
var txtH = lines.length * lh;
var h = y + lh + height;
// 如果高度大于总高度则垂直居中
var y = height > txtH ? y + Math.ceil((height - txtH) * 0.5) : y
for (var line of lines) {
y += lh
if (y > h) { break; }
context.fillText(line, cell.x + 5, y);
}
return true;
}
return false;
}
七、状态存储
// 存储
context.save();
// 恢复
context.restore();
八、裁剪
// 先绘制路径,再裁剪
context.clip();
九、风格
9.1 填充
context.fillStyle = 'red';
context.fill();
9.2 勾勒
context.strokeStyle = 'red';
context.stroke();
9.3 线性渐变
var grd = context.createLinearGradient(x1, y1, x2, y2);
grd.addColorStop(0, 'red');
grd.addColorStop(1, 'blue');
context.fillStyle = grd;
context.fill();
9.4 径向渐变
var grd = context.createRadialGradient(x1, y1, radius1, x2, y2, radius2);
grd.addColorStop(0, 'red');
grd.addColorStop(1, 'blue');
context.fillStyle = grd;
context.fill();
9.5 图案
var imageObj = new Image();
imageObj.onload = function() {
var pattern = context.createPattern(imageObj, 'repat');
context.fillStyle = pattern;
context.fill();
}
imageObj.src = 'path/to/my/image.jpg';
9.6 交点
context.lineJoin = 'miter|round|bevel';
9.7 线头
context.lineCap = 'butt|round|square';
9.8 阴影
context.shadowColor = 'black';
context.shadowBlur = 20;
context.shadowOffsetX = 10;
context.shadowOffsetY = 10;
9.9 透明 (Alpha)
context.globalAlpha = 0.5; // between 0 and 1
十、合成
10.1 合成操作
context.globalCompositeOperation = 'source-atop|source-in|source-out|source-over|destination-atop|destination-in|destination-out|destination-over|lighter|xor|copy';
十一、 Data URLS
11.1 获取Data URL
var dataUrl = canvas.toDataURL();
11.2 使用Data URL生成图像
var imageObj = new Image();
imageObj.onload = function() {
context.drawImage(imageObj, 0, 0);
}
imageObj.src = dataUrl;
十二、 图像数据
12.1 获取图像数据
var imageData = context.getImageData(x, y, width, height);
var data = imageData.data;
12.2 遍历像素点
var imageData = context.getImageData(x, y, width, height);
var data = imageData.data;
var len = data.length;
var i, r, g, b, a;
for (i=0; i<len; i+=4) {
r = data[i]; // red
g = data[i+1]; // green
b = data[i+2]; // blue
a = data[i+3]; // alpha
}
12.3 沿坐标遍历像素点
var imageData = context.getImageData(x, y, width, height);
var data = imageData.data;
var len = data.length;
var x, y, r, g, b, a;
for (y=0; i<imageHeight; y++) {
var sy = imageWidth * y;
for (x=0; x<imageWidth; x++) {
var i = (sy + x) * 4;
r = data[i];
g = data[i+1];
b = data[i+2];
a = data[i+3];
}
}
12.4 设置图像数据
context.putImageData(imageData, x, y);
十三、 动画
13.1 移动
context.translate(x, y);
13.2 扩大缩小
context.scale(x, y);
13.3 旋转
context.rotate(radians);
13.4 水平翻转
context.scale(-1, 1);
13.5 上下翻转
context.scale(1, -1);
13.6 自定义变换
context.transform(a, b, c, d, e, f);
13.7 设置变换
context.setTransform(a, b, c, d, e, f);
13.8 切割
context.transform(1, sy, sx, 1, 0, 0);
13.9 重置
context.setTransform(1, 0, 0, 1, 0, 0);