HTML5 添加的最受欢迎的功能就是<canvas>元素。这个元素负责在页面中设定一个区域,然后就可以通过JavaScript 动态地在这个区域中绘制图形。
15.1 基本用法
要使用<canvas>元素,必须先设置其 width 和 height 属性,指定可以绘图的区域大小。
<canvas id="drawing" width=" 200" height="200">A drawing of something.</canvas>
与其他元素一样,<canvas>元素对应的 DOM 元素对象也有 width 和 height 属性
要在这块画布(canvas)上绘图,需要取得绘图上下文。需要调用getContext()方法并传入上下文的名字。传入"2d",就可以取得 2D 上下文对象。
var drawing = document.getElementById("drawing");
//确定浏览器支持<canvas>元素
if (drawing.getContext){
var context = drawing.getContext("2d");
//更多代码
}
使用 toDataURL()方法,可以导出在<canvas>元素上绘制的图像。这个方法接受一个参数,即图像的 MIME 类型格式,而且适合用于创建图像的任何上下文
var drawing = document.getElementById("drawing");
//确定浏览器支持<canvas>元素
if (drawing.getContext){
//取得图像的数据 URI
var imgURI = drawing.toDataURL("image/png");
//显示图像
var image = document.createElement("img");
image.src = imgURI;
document.body.appendChild(image);
}
15.2 2D 上下文
使用 2D 绘图上下文提供的方法,可以绘制简单的 2D 图形,比如矩形、弧线和路径。2D 上下文的坐标开始于<canvas>元素的左上角,原点坐标是(0,0)。x 值越大表示越靠右,y 值越大表示越靠下。
15.2.1 填充和描边
填充,就是用指定的样式(颜色、渐变或图像)填充图形;描边,就是只在图形的边缘画线。它们的结果结果取决于两个属性:fillStyle 和 strokeStyle。
var drawing = document.getElementById("drawing");
//确定浏览器支持<canvas>元素
if (drawing.getContext){
var context = drawing.getContext("2d");
context.strokeStyle = "red";
context.fillStyle = "#0000ff";
}
15.2.2 绘制矩形
矩形是唯一一种可以直接在 2D 上下文中绘制的形状。与矩形有关的方法包括 fillRect()、strokeRect()和 clearRect()。。这三个方法都能接收 4 个参数:矩形的 x 坐标、矩形的 y 坐标、矩形宽度和矩形高度。
fillRect()画实心填充矩形
var drawing = document.getElementById("drawing");
//确定浏览器支持<canvas>元素
if (drawing.getContext){
var context = drawing.getContext("2d");
//绘制红色矩形
context.fillStyle = "#ff0000";
context.fillRect(10, 10, 50, 50);
//绘制半透明的蓝色矩形
context.fillStyle = "rgba(0,0,255,0.5)";
context.fillRect(30, 30, 50, 50);
}
strokeRect()画空心矩形
var drawing = document.getElementById("drawing");
//确定浏览器支持<canvas>元素
if (drawing.getContext){
var context = drawing.getContext("2d");
//绘制红色描边矩形
context.strokeStyle = "#ff0000";
context.strokeRect(10, 10, 50, 50);
//绘制半透明的蓝色描边矩形
context.strokeStyle = "rgba(0,0,255,0.5)";
context.strokeRect(30, 30, 50, 50);
}
clearRect()方法用于清除画布上的矩形区域
15.2.3 绘制路径
要绘制路径,首先必须调用 beginPath()方法,表示要开始绘制新路径。然后,再通过调用下列方法来实际地绘制路径。
-
arc(x, y, radius, startAngle, endAngle, counterclockwise):以(x,y)为圆心绘制一条弧线,弧线半径为 radius,起始和结束角度(用弧度表示)分别为 startAngle 和endAngle。最后一个参数表示 startAngle 和 endAngle 是否按逆时针方向计算,值为 false表示按顺时针方向计算。
-
arcTo(x1, y1, x2, y2, radius):从上一点开始绘制一条弧线,到(x2,y2)为止,并且以给定的半径 radius 穿过(x1,y1)。
-
bezierCurveTo(c1x, c1y, c2x, c2y, x, y):从上一点开始绘制一条曲线,到(x,y)为止,并且以(c1x,c1y)和(c2x,c2y)为控制点。
-
lineTo(x, y):从上一点开始绘制一条直线,到(x,y)为止。
-
moveTo(x, y):将绘图游标移动到(x,y),不画线。
-
quadraticCurveTo(cx, cy, x, y):从上一点开始绘制一条二次曲线,到(x,y)为止,并且以(cx,cy)作为控制点。
-
rect(x, y, width, height):从点(x,y)开始绘制一个矩形,宽度和高度分别由 width 和height 指定。这个方法绘制的是矩形路径,而不是 strokeRect()和 fillRect()所绘制的独立的形状。
15.2.4 绘制文本
2D 绘图上下文也提供了绘制文本的方法。绘制文本主要有两个方法:fillText()和 strokeText()。fillText()方法使用fillStyle 属性绘制文本,而 strokeText()方法使用 strokeStyle 属性为文本描边。
15.2.5 变换
可以通过如下方法来修改变换矩阵。
- rotate(angle):围绕原点旋转图像 angle 弧度。
- scale(scaleX, scaleY):缩放图像,在 x 方向乘以 scaleX,在 y 方向乘以 scaleY。scaleX和 scaleY 的默认值都是 1.0。
- translate(x, y):将坐标原点移动到(x,y)。执行这个变换之后,坐标(0,0)会变成之前由(x,y)表示的点。
- transform(m1_1, m1_2, m2_1, m2_2, dx, dy):直接修改变换矩阵,方式是乘以如下矩阵。
- setTransform(m1_1, m1_2, m2_1, m2_2, dx, dy):将变换矩阵重置为默认状态,然后再调用 transform()。
15.2.6 绘制图像
把一幅图像绘制到画布上,可以使用 drawImage()方法。
var image = document.images[0];
context.drawImage(image, 10, 10);
15.2.7 阴影
2D 上下文会根据以下几个属性的值,自动为形状或路径绘制出阴影。
- shadowColor:用 CSS 颜色格式表示的阴影颜色,默认为黑色。
- shadowOffsetX:形状或路径 x 轴方向的阴影偏移量,默认为 0。
- shadowOffsetY:形状或路径 y 轴方向的阴影偏移量,默认为 0。
- shadowBlur:模糊的像素数,默认 0,即不模糊。
15.2.8 渐变
渐变由 CanvasGradient 实例表示,很容易通过 2D 上下文来创建和修改。创建了渐变对象后,下一步就是使用 addColorStop()方法来指定色标。
var gradient = context.createLinearGradient(30, 30, 70, 70);
gradient.addColorStop(0, "white");
gradient.addColorStop(1, "black");
15.2.9 模式
模式其实就是重复的图像,可以用来填充或描边图形。要创建一个新模式,可以调用createPattern()方法。
var image = document.images[0],
pattern = context.createPattern(image, "repeat");
//绘制矩形
context.fillStyle = pattern;
context.fillRect(10, 10, 150, 150);
15.2.10 使用图像数据
2D 上下文的一个明显的长处就是,可以通过 getImageData()取得原始图像数据。这个方法接收4 个参数:要取得其数据的画面区域的 x 和 y 坐标以及该区域的像素宽度和高度。
var imageData = context.getImageData(10, 5, 50, 50);
15.2.11 合成
还有两个会应用到 2D 上下文中所有绘制操作的属性:globalAlpha 和 globalCompositionOperation。
//绘制红色矩形
context.fillStyle = "#ff0000";
context.fillRect(10, 10, 50, 50);
//修改全局透明度
context.globalAlpha = 0.5;
//绘制蓝色矩形
context.fillStyle = "rgba(0,0,255,1)";
context.fillRect(30, 30, 50, 50);
//重置全局透明度
context.globalAlpha = 0;
15.3 WebGL
WebGL 是针对 Canvas 的 3D 上下文。与其他 Web 技术不同,WebGL 并不是 W3C 制定的标准,而是由 Khronos Group 制定的。
15.3.1 类型化数组
WebGL 引入了一个概念,叫类型化数组(typed arrays)。类型化数组也是数组,只不过其元素被设置为特定类型的值。
类型化数组的核心就是一个名为 ArrayBuffer 的类型
15.3.2 WebGL上下文
WebGL 的名字叫"experimental-webgl"
var drawing = document.getElementById("drawing");
//确定浏览器支持<canvas>元素
if (drawing.getContext){
var gl = drawing.getContext("experimental-webgl");
if (gl){
//使用 WebGL
}
}
一般都把WebGL上下文对象命名为gl。大多数WebGL应用和示例都遵守这一约定,因为 OpenGL ES 2.0 规定的方法和值通常都以"gl"开头。