轻松入门Canvas~ 弹球碰撞小游戏

写在开头
利用canvas写的弹球碰撞小游戏,体验地址,练习canvas!
本文只展示部分代码,详细代码见 Gitee github
实现过程
1.设置画布
先生成一个黑色背景充满当前窗口,便于后续实现小球移动
1 2 3 4 5
| const canvas = document.querySelector('canvas'); const ctx = canvas.getContext('2d'); const width = canvas.width = window.innerWidth; const height = canvas.height = window.innerHeight; ctx.fillRect (0,0, width, height);
|
2.生成随机小球
先画出小球,比较简单,就是只画出一个圆
1 2 3 4 5
| ctx.beginPath(); ctx.fillStyle = 'red'; ctx.arc(95,50,40,0,2*Math.PI); ctx.fill() ctx.closePath()
|

一个小球肯定不够,所以我们要实现多个随机位置、随机颜色、随机大小的小球
增加随机方法
1 2 3 4
| function random(min, max) { const num = Math.floor(Math.random() * (max - min)) + min; return num; }
|
获取全随机值
1 2 3 4 5 6 7 8 9
| function Ball(width, height, ctx) { this.width = width; this.height = height; this.ctx = ctx; this.r = random(10, 20); this.x = random(this.r, this.width - this.r); this.y = random(this.r, this.height - this.r) this.color = `rgb(${random(0, 255)},${random(0, 255)},${random(0, 255)})`; }
|
加入循环多次调用,生成小球实例,即可实现多个随机小球了

3.小球实现移动、碰撞变色
小球移动
实现移动,就是改变小球的坐标值,所以需要给小球加一个速度值
1
| ctx.arc(x,y,r,0,2*Math.PI);
|
即改变x、y值。这个速度值也可以随机生成,加入正负,即可实现上下左右移动。
1 2 3 4 5 6 7
| this.speedX = random(-4, 4); this.speedY = random(-4, 4);
move: function () { this.x += this.speedX; this.y += this.speedY; },
|
这个时候会出现一些问题,随机速度为零,球就不移动了,这个这个加入判断即可
另一种情况,球到边界了,此时再移动就出去了,这个时候就把速度取反
//解决生成球不动情况
if (this.speedX == 0) {
this.speedX = 1;
}
if (this.speedY == 0) {
this.speedY = 1;
}
//判断边界值,让圆球始终保证在画面内
if (this.x > this.width - this.r || this.x < this.r) {
this.speedX = -this.speedX;
}
if (this.y > this.height - this.r || this.y < this.r) {
this.speedY = -this.speedY;
}
碰撞变色
实现碰撞其实也很简单,两个小球之间只需要判断他们的位置距离是否超过它们半径和即可,
然后再赋予他们随机变色
1 2 3
| if (Math.sqrt(Math.pow(balls[j].x - balls[k].x, 2) + Math.pow(balls[j].y - balls[k].y, 2)) <= balls[k].r + balls[j].r) { balls[j].color = balls[k].color = `rgb(${random(0, 255)},${random(0, 255)},${random(0, 255)})`; }
|
.gif)
4.控制球吃球
控制球移动,就需要绑定键盘的事件,用键盘控制移动速度,这里设置ctrl加速
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
| document.onkeydown = function (event) { var speed = 30; if (event.ctrlKey) { speed = 100; } switch (event.code) { case "ArrowLeft": that.x = that.x - speed; break; case "ArrowRight": that.x = that.x + speed; break; case "ArrowUp": that.y = that.y - speed; break; case "ArrowDown": that.y = that.y + speed; break; } };
|
然后判断相撞,依然是用距离和半径比较,撞后小球消失,玩家小球增大
1 2 3 4 5
| if (Math.sqrt(Math.pow(balls[j].x - playerBall.x, 2) + Math.pow(balls[j].y - playerBall.y, 2)) <= playerBall.r + balls[j].r) { balls.splice(j, 1); playerBall.r = playerBall.r + 5; }
|
5.增加尾迹
为了让小球更加美观,加入尾迹,每次重新画布时增加透明度即可
1 2
| ctx.fillStyle = "rgba(0,0,0,0.2)" ctx.fillRect(0, 0, width, height);
|
这就实现了完整效果

写在结尾
这就是对canvas的一个小练习,欢迎进一步拓展!