JavaScript 是前端核心, 掌握这门语言是步入前端高手行列必经之路,噢,别忘了还有TypeScript, 学习它还需要OOP知识, 底层的浏览器原理、HTTP协议也必不可少, 此系列文章记录使用JavaScript和Canvas进行游戏开发, 有游戏才有趣!!!
(一) JavaScript Canvas 画线
1. 准备HTML页面
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| <!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 { position: absolute; background: white; width: 100%; height: 100%; top: 0; left: 0; } canvas { background: linear-gradient(120deg, #4a3934, #e6d5b9); } </style> </head> <body> <canvas id="canvas"></canvas> <script> </script> </body>
|
2. 画线
- 掌握几个函数
- translate() 平移坐标原点到指定坐标位置
- moveTo(0, 0) 移动到坐标位置(0, 0)
- beginPath() 开始路径
- closePath() 关闭路径
- rotate() 旋转
- save()
- 画一根线
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| <script> const canvas = document.getElementById('canvas') const ctx = canvas.getContext('2d') canvas.width = window.innerWidth canvas.height = window.innerHeight ctx.translate(canvas.width/2, canvas.height/2) ctx.moveTo(0, 0) ctx.lineTo(200, 0) ctx.strokeStyle = "black" ctx.lineWidth = 5 ctx.stroke() </script>
|
如下图所示,注意此时并没有使用beginPath()也没有使用closePath()
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| <script> const canvas = document.getElementById('canvas') const ctx = canvas.getContext('2d') canvas.width = window.innerWidth canvas.height = window.innerHeight ctx.translate(canvas.width/2, canvas.height/2) ctx.moveTo(0, 0) ctx.lineTo(200, 0) ctx.strokeStyle = "black" ctx.lineWidth = 5 ctx.stroke() ctx.strokeStyle = "red" ctx.lineTo(200, 30) ctx.lineWidth = 5 ctx.stroke() </script>
|
结果如图所示: 第一根线的样式完全变成了第二根线的样式,原因是画完第一根线时并没有关闭路径,也就是没有调用closePath()方法,导致第二根线的起始点会在第一根的结束坐标开始
- 在画完第一根线后closePath(), 关闭路径后,下一根线的起点将从原点(0,0)开始, 但是第一根线的颜色从black变成了red
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
| <script> const canvas = document.getElementById('canvas') const ctx = canvas.getContext('2d') canvas.width = window.innerWidth canvas.height = window.innerHeight ctx.translate(canvas.width/2, canvas.height/2) ctx.moveTo(0, 0) ctx.lineTo(200, 0) ctx.strokeStyle = "black" ctx.lineWidth = 10 ctx.stroke() ctx.closePath() ctx.strokeStyle = "red" ctx.lineTo(200, 20) ctx.lineWidth = 5 ctx.stroke() </script>
|
- 为了让每一根线的样子能独立出来,相互不影响,需要使用beginPath() 顾名思义就是开始路径
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| <script> const canvas = document.getElementById('canvas') const ctx = canvas.getContext('2d') canvas.width = window.innerWidth canvas.height = window.innerHeight ctx.translate(canvas.width/2, canvas.height/2) ctx.beginPath() ctx.moveTo(0, 0) ctx.lineTo(200, 0) ctx.strokeStyle = "black" ctx.lineWidth = 10 ctx.stroke() ctx.closePath() ctx.beginPath() ctx.strokeStyle = "red" ctx.moveTo(0,0) ctx.lineTo(200, 20) ctx.lineWidth = 5 ctx.stroke() </script>
|
- 下面利用旋转函数rotate画出下面的图形, 需要知晓以下数学知识
- 1弧度是 大约 57.2958角度
- 将弧度转换为角度:乘以 180,除以 π
- 将角度转换为弧度:乘以 π,除以 180
- 弧度是基于圆的半径的纯计量单位
- 在一个半圆上有 π 弧度,也等于 180°, 所以: π 弧度 = 180° 那么 : 1弧度 = 180°/π = 57.2958……°
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49
| <script>
const canvas = document.getElementById('canvas') const ctx = canvas.getContext('2d') canvas.width = window.innerWidth canvas.height = window.innerHeight ctx.translate(canvas.width/2, canvas.height/2)
ctx.beginPath() ctx.moveTo(0, 0) ctx.lineTo(200, 0) ctx.strokeStyle = "black" ctx.lineWidth = 10 ctx.stroke() ctx.closePath() ctx.beginPath() ctx.rotate(30*Math.PI/180) ctx.strokeStyle = "red" ctx.moveTo(0,0) ctx.lineTo(200, 0) ctx.lineWidth = 5 ctx.stroke() ctx.beginPath() ctx.rotate(30*Math.PI/180) ctx.strokeStyle = "yellow" ctx.moveTo(0,0) ctx.lineTo(200, 0) ctx.lineWidth = 5 ctx.stroke()
ctx.beginPath() ctx.rotate(30*Math.PI/180) ctx.strokeStyle = "pink" ctx.moveTo(0,0) ctx.lineTo(200, 0) ctx.lineWidth = 5 ctx.stroke() </script>
|
- 如果再加上**ctx.save()和ctx.restore()**函数,看看有什么区别? 把第三根线加上save和restore方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52
| <script>
const canvas = document.getElementById('canvas') const ctx = canvas.getContext('2d') canvas.width = window.innerWidth canvas.height = window.innerHeight ctx.translate(canvas.width/2, canvas.height/2)
ctx.beginPath() ctx.moveTo(0, 0) ctx.lineTo(200, 0) ctx.strokeStyle = "black" ctx.lineWidth = 10 ctx.stroke() ctx.closePath() ctx.beginPath() ctx.rotate(30*Math.PI/180) ctx.strokeStyle = "red" ctx.moveTo(0,0) ctx.lineTo(200, 0) ctx.lineWidth = 5 ctx.stroke() ctx.save() ctx.beginPath() ctx.rotate(30*Math.PI/180) ctx.strokeStyle = "yellow" ctx.moveTo(0,0) ctx.lineTo(200, 0) ctx.lineWidth = 5 ctx.stroke() ctx.restore()
ctx.beginPath() ctx.rotate(30*Math.PI/180) ctx.strokeStyle = "pink" ctx.moveTo(0,0) ctx.lineTo(200, 0) ctx.lineWidth = 5 ctx.stroke() </script>
|
结果是第四根线不再依据第三根线旋转角度,而是依据第二根红线旋转角度,对于第四根线来说就好像第三根线不存在一样, 据此可以明白save() restore()的作用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
| <script>
const canvas = document.getElementById('canvas') const ctx = canvas.getContext('2d') canvas.width = window.innerWidth canvas.height = window.innerHeight ctx.translate(canvas.width/2, canvas.height/2)
drawLine();
function drawLine() { ctx.translate(canvas.width/2, canvas.height/2) for(let i=0;i<12;i++) { ctx.beginPath() ctx.strokeStyle = 'hsl('+Math.random()*360+",100%,50%)" ctx.lineWidth = 5 ctx.rotate(30*Math.PI/180) ctx.lineTo(0, 0) ctx.lineTo(200, 0) ctx.stroke() ctx.closePath() } } </script>
|
效果如下图:
利用上面所了解的知识点,能画出一个五角星吗? 下一篇来试试