> 文章列表 > canvas的基础讲解

canvas的基础讲解

canvas的基础讲解

目录

一、低版本浏览器不显示canvas, 并给出提示

二、canvas是一个行内元素,想要居中就需要把他变成块元素

三、画线

 四、画矩形

五、清除画布

 六、画圆

七、画圆弧


一、低版本浏览器不显示canvas, 并给出提示

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><!-- canvas在低版本中不兼容,需要提示用户 --><canvas width="500px" height="500px">您的浏览器版本过低,请升级浏览器或者使用chrome打开!</canvas>
</body>
</html>

能显示canvas就没有文字提示,不显示canvas就显示提示文字

二、canvas是一个行内元素,想要居中就需要把他变成块元素

<!DOCTYPE html>
<html lang="en">
<head><style>canvas {display: block;margin: 0 auto;border: 1px solid #aaa;}</style>
</head>
<body><!-- canvas在低版本中不兼容,需要提示用户 --><canvas width="500px" height="500px">您的浏览器版本过低,请升级浏览器或者使用chrome打开!</canvas>
</body>
</html>

 效果:

三、画线

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>// 只能使用原生js操作canvas, jq不可以// 画一条线的步骤//(1)获取画布var canvas = document.querySelector("#cont");//(2)获取画布的能力var ctx = canvas.getContext("2d");// (3)开始一条路径ctx.beginPath();// (4)确定起点ctx.moveTo(100, 100);// (5)确定结束点ctx.lineTo(400, 400);// 添加线宽和颜色  (这个必须在着色之前写)// 设置颜色ctx.strokeStyle = 'green'// 设置线宽ctx.lineWidth=5// (6)着色ctx.stroke();// (7)结束路径ctx.closePath();</script>
</body>
</html>

效果:

四、画虚线

 语法:

ctx.setLineDash([虚线长度, 虚线间隔])
drawLine(起始点的x坐标, 起始点的y坐标, 终点的x坐标, 终点的y坐标, 虚线的颜色 )

四、画矩形

rect(x, y, width, height)  // 可描边、填充
fillRect(x, y, width, height)  // 不可描边、只能填充
strokeRect(x, y, width, height)  // 只能描边、不可填充
x 矩形左上角的x坐标
y 矩形左上角的y坐标
width 矩形的宽度,以像素为单位
height 矩形的高度,以像素为单位

注意: 注意需要填充和描边的   先填充后描边   否则填充会压着描边

案例:

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>//(1)获取画布var canvas = document.querySelector("#cont");//(2)获取画布的能力var ctx = canvas.getContext("2d");/* rect(x, y, width, height) // 有描边也有填充*/ctx.rect(100, 100, 300, 200)// 填充 ctx.fillStyle = "red"ctx.fill();// 描边ctx.strokeStyle = 'blue'ctx.lineWidth=5ctx.stroke();/* fillRect(x, y, width, heihgt)  // 只能填充, 不可描边*/ctx.fillStyle = 'pink'ctx.fillRect(100, 400, 100, 1000)/* strokeRect(x, y, width, heihgt)*/ctx.strokeStyle= 'gold'ctx.strokeRect(300, 400, 100, 100)ctx.closePath();</script>
</body>
</html>

 效果:

五、清除画布

语法:

clearRect(x, y, width, height)

案例:

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>//(1)获取画布var canvas = document.querySelector("#cont");//(2)获取画布的能力var ctx = canvas.getContext("2d");ctx.rect(100, 100, 300, 200)// 填充 ctx.fillStyle = "red"ctx.fill();// 描边ctx.strokeStyle = 'blue'ctx.lineWidth=5ctx.stroke();// 清除画布ctx.clearRect(120, 120,200, 100)ctx.closePath();</script>
</body>
</html>

效果:

 六、画圆

语法:

arc(x, y, radius, startAngle, endAngle, counterclockwise)

参数

x 圆心 x 坐标
y 圆心 y 坐标
radius 半径
startAngle 开始的角度
endAngle 结束的角度
counterclockwise true: 逆时针、false: 顺时针

案例:

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>//(1)获取画布var canvas = document.querySelector("#cont");//(2)获取画布的能力var ctx = canvas.getContext("2d");ctx.arc(250, 250, 200, 0, Math.PI*2, false)ctx.fillStyle = 'gold'ctx.fill()ctx.lineWidth = 10;ctx.strokeStyle = 'red'ctx.stroke()ctx.closePath();</script>
</body>
</html>

效果:

七、画圆弧

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>//(1)获取画布var canvas = document.querySelector("#cont");//(2)获取画布的能力var ctx = canvas.getContext("2d");ctx.beginPath()ctx.arc(100, 100, 100, 0, Math.PI*1, true)ctx.stroke()ctx.beginPath()  // 当前使用了新了一个beginPath()   所以上一个不需要closePath   因为他默认给你加上了ctx.arc(300, 100, 100, 0, Math.PI*1, false)ctx.stroke()ctx.closePath();</script>
</body>
</html>

注意: 当前使用了新了一个beginPath()   所以上一个不需要closePath   因为他默认给你加上了

八、绘制图片

方式一

// 在画布上定位图像
ctx.drawImage(img, x, y)

 方式二

// 在画布上定位图像  并规定图像的宽、高
ctx.drawImage(img, x, y, width, height)

方式三

// 剪切图像,并在画布上定位被裁剪的部分
ctx.drawImage(img, sx, sy, swidth, sheight, x, y, width, height)

 参数:

img 要使用的图像、画布、视频
sx 可选。开始剪切的 x 坐标
sy 可选。开始剪切的 y 坐标
swidth 可选。被剪切图像的宽度
sheight 可选。被剪切图像的高度
x 在画布上放置图像的 x 坐标
y 在画布上放置图像的 y 坐标
width 可选。 要使用的图像的宽度。(伸展或缩小图像)
height 可选。 要使用的图像的高度。(伸展或缩小图像)

八、案例:小球碰壁检测

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>//(1)获取画布var canvas = document.querySelector("#cont");//(2)获取画布的能力var ctx = canvas.getContext("2d");// 画布宽高var w=h=500;var x = 100;var y = 100;var r = 30;// 水平速度var xSpeed = 10;// 垂直运动var ySpeed = 6;setInterval(function() {// 每次都要清除整个画布ctx.clearRect(0, 0, w, h);// 在小球碰到边缘时,速度取相反即可if(x-r <= 0 || x+r > w ) {xSpeed = -xSpeed;}x = x+xSpeedif(y-r <= 0 || y+r > w ) {ySpeed = -ySpeed;}y = y+ySpeed// 水平运动drawCircle(x, y, r);}, 50)function drawCircle(x, y, r) {// 加这个相当于把上面一次的画笔清除掉  否则就相当于你的笔重来都没有离开过画布ctx.beginPath()ctx.arc(x, y, r, 0, Math.PI*2);ctx.fillStyle = 'gold'ctx.fill()}</script>
</body>
</html>

效果:碰到周围就会反弹

 九、案例:小球碰壁检测(面向对象)

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>//(1)获取画布var canvas = document.querySelector("#cont");//(2)获取画布的能力var ctx = canvas.getContext("2d");// 画布宽高var w = 500var h = 500var ballArr = []/* 面向对象* */function r(num) {return Math.random()*num}/* @param x       起始x坐标* @param y       起始y坐标* @param r       小球半径* @param color   小球颜色* @param xSpeed  x轴速度* @param ySpeed  y轴速度* @author: @郑建*/        function Ball() {this.x = r(5) + 60;this.y = r(3) + 60;this.r = r(50) + 10 // [10, 100)this.color = '#' + parseInt(Math.random()*0xffffff).toString(16)this.xSpeed = r(3) + 2;  // [2, 5)this.ySpeed = r(3) + 1;  // [1, 4)}// 在原型链上定义小球的公共方法Ball.prototype.show = function() {this.run()ctx.beginPath();ctx.arc(this.x, this.y, this.r, 0, Math.PI*2);ctx.fillStyle = this.colorctx.fill();}// 在原型链上定义小球的公共方法Ball.prototype.run = function() {if(this.x-this.r <= 0 || this.x+this.r >= w) {this.xSpeed = -this.xSpeed}this.x = this.x + this.xSpeedif(this.y-this.r <= 0 || this.y+this.r >= w) {this.ySpeed = -this.ySpeed}this.y = this.y + this.ySpeed}for(var i = 0; i < 1000; i++) {var ball = new Ball()ballArr.push(ball)ball.show()}setInterval(function() {ctx.clearRect(0, 0, w, h)for(var i = 0; i < ballArr.length; i++) {var ball = ballArr[i]ball.show()}}, 20)</script>
</body>
</html>

 效果:

十、画文字

1、基础显示

语法:

fillText(text, x, y, maxWidth);  // 实心文字
strokeText(text, x, y, maxWidth);  // 空心文字

参数:

text 画布上输出的文本
x 开始绘制文本的x坐标位置
y 开始绘制文本的y坐标位置
maxWidth 可选。允许的最大文本宽度,

案例一:

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>var canvas = document.querySelector("#cont");var ctx = canvas.getContext("2d");// 1.设置字体样式// fontctx.font = '30px 微软雅黑';//字体颜色ctx.fillStyle = 'gold'// 2.画文字ctx.fillText('实心文字', 250, 250)//  空心文字ctx.strokeStyle = 'red'ctx.strokeText('空心文字', 0, 250)//  未设置最大宽度ctx.fillStyle = 'red'ctx.fillText('你好!我是未设置最大宽度的字体', 100, 50)//  设置最大宽度ctx.fillStyle = 'green'ctx.fillText('你好!我设置最大宽度的字体', 100, 100, 300)</script>
</body>
</html>

效果:

2、文字渐变

语法:

var gradient = ctx.createLinearGradient(x0, y0, x1, y1)

 参数:

x0 渐变开始点的 x 坐标
y0 渐变开始点的 y 坐标
x1 渐变结束点的 x 坐标
y1 渐变结束点的 y 坐标

案例:

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Document</title><style>canvas {display: block;margin: 0 auto;border: 1px solid #aaa;}</style> 
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>var canvas = document.querySelector("#cont");var ctx = canvas.getContext("2d");ctx.font = '50px 微软雅黑';/* 设置线性渐变*/var gradient = ctx.createLinearGradient(0, 0, canvas.width, 0)gradient.addColorStop('0', "yellow")gradient.addColorStop('0.5', 'blue')gradient.addColorStop('1.0', 'red')ctx.fillStyle = gradientctx.fillText('今天天气不错, 风和日丽!', 0, 100, 500)ctx.strokeStyle = gradientctx.strokeText('适合出去玩儿!happy~', 0, 300, 500)</script>
</body>
</html>

 效果:

 3、文字位置

语法:

textAlign = 'start' | 'end' | 'left' | 'right' | 'center'   // 水平方向
textBaseLine = 'top' | 'bottom' | 'moddle' | 'alphabetic' | 'hanging'

像素点

语法: 

ctx.getImageData(x, y, width, height)

参数:

x 开始复制的左上角位置的 x 坐标
y 开始复制的左上角位置的 y 坐标
width 将要复制的矩形区域的宽度
height 将要复制的矩形区域的高度

介绍:

返回的getImageData对象,该对象拷贝了画布指定矩形的像素数据

对于getImageData对象中的每个像素,都存在着四方面的信息, 即RGBA值

R - 红色 (0 - 255)  

G - 绿色 (0 - 255)  

B - 蓝色 (0 - 255)  

A - alpha 通道 (0 - 255) ; 0: 透明; 255:完全不透明

color / alpha 以数组的形式存在,并存储于getImage对象的data属性中   

案例:

<!DOCTYPE html>
<html lang="en">
<head> 
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>var canvas = document.querySelector("#cont");var ctx = canvas.getContext("2d");// 1 创建图片var img = new Image();img.src = 'u10.png'img.onload = function() {// 2 绘制图片ctx.drawImage(img, 0, 0, img.width, img.height)// 3 获取像素点var copy = ctx.getImageData(0, 0, 10, 10);console.log('像素数据', copy);}</script>
</body>
</html>

打印:

 

把像素点放到画布上

语法:

putImageData(imgData, x, y, dirtyX, dirtyY, dirtyWidth, dirtyHeight)

参数:

imgData 规定要放回画布的ImageData对象
x ImageData对象左上角的 x 坐标,以像素计
ImageData对象左上角的 y 坐标,以像素计
dirtyX 可选。 水平值(x), 在画布上放置图片的位置
dirtyY 可选。 水平值(y), 在画布上放置图片的位置
dirtyWidth 可选。 在画布上绘制图像所使用的宽度
dirtyHeight 可选。 在画布上绘制图像所使用的高度

案例:

<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body><canvas id="cont" width="500px" height="500px"></canvas><script>var canvas = document.querySelector("#cont");var ctx = canvas.getContext("2d");// 1 创建图片var img = new Image();img.src = 'u10.png'img.onload = function() {// 2 绘制图片ctx.drawImage(img, 0, 0, 250, 250)// 3 获取像素点var copy1 = ctx.getImageData(0, 0, 100, 100);ctx.putImageData(copy1, 0, 350)}</script>
</body>
</html>

效果: