canvas ,js 实现一个简单的飞机大战
代码:
<!DOCTYPE html>
<html>
<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 #000;
}
</style>
</head>
<body>
<canvas></canvas>
<script>
var canvas = document.getElementsByTagName('canvas')[0];
var ctx = canvas.getContext('2d');
var canvasParam = {
width: 480,
height: 852
}
canvas.width = canvasParam.width;
canvas.height = canvasParam.height;
var ready = 0;
var loading = 1;
var running = 2;
var pause = 3;
var gameOver = 4;
var gameState = ready;
var life = 3;
var score = 0;
var bgSrc = new Image();
bgSrc.src = 'img/background.png';
var bgParam = {
bgSrc: bgSrc,
x: 0,
y: 0,
width: 480,
height: 852
}
function Bg(param) {
this.bgSrc = param.bgSrc;
this.x = param.x;
this.y = param.y;
this.y1 = param.y1;
this.width = param.width;
this.height = param.height;
this.y1 = -this.height;
this.paint = function() {
ctx.drawImage(this.bgSrc, this.x, this.y, this.width, this.height);
ctx.drawImage(this.bgSrc, this.x, this.y1, this.width, this.height);
}
this.sport = function() {
this.y += 5;
this.y1 += 5;
if (this.y >= this.height) {
this.y = -this.height;
}
if (this.y1 >= this.height) {
this.y1 = -this.height;
}
}
}
var bgObj = new Bg(bgParam);
var logoSrc = new Image();
logoSrc.src = 'img/start.png';
var logoParam = {
logoSrc: logoSrc,
x: 0,
y: 0,
width: 480,
height: 852
}
function Logo(param) {
this.logoSrc = param.logoSrc;
this.x = param.x;
this.y = param.y;
this.width = param.width;
this.height = param.height;
this.paint = function() {
ctx.drawImage(this.logoObj, this.x, this.y, this.width, this.height);
}
}
var logoObj = new Logo(logoParam);
canvas.onclick = function() {
if (gameState === ready) {
gameState = loading;
}
}
var loadImgArr = ['img/game_loading1.png', 'img/game_loading2.png', 'img/game_loading3.png', 'img/game_loading4.png']
var loadingImg = [];
for (var i = 0; i < loadImgArr.length; i++) {
loadingImg[i] = new Image();
loadingImg[i].src = loadImgArr[i];
}
var loadingParam = {
loadingImg: loadingImg,
x: 0,
width: 186,
height: 38
}
function Loading(param) {
this.loadingImg = loadingImg;
this.width = param.width;
this.height = param.height;
this.x = param.x;
this.y = canvasParam.height - param.height;
this.index = 0;
this.num = 0;
this.paint = function() {
ctx.drawImage(this.loadingImg[this.index], this.x, this.y, this.width, this.height);
}
this.sport = function() {
this.num++;
if (this.num % 5 == 0) {
this.index++;
if (this.index === this.loadingImg.length) {
gameState = running;
}
}
}
}
var loadingObj = new Loading(loadingParam);
var heroImgs = [
'img/hero1.png',
'img/hero2.png',
'img/hero1.png',
'img/hero_blowup_n1.png',
'img/hero_blowup_n2.png',
'img/hero_blowup_n3.png',
'img/hero_blowup_n4.png'
]
var heroRunning = [];
for (var i = 0; i < heroImgs.length; i++) {
heroRunning[i] = new Image();
heroRunning[i].src = heroImgs[i];
}
var heroParam = {
haroRunning: heroRunning,
width: 99,
height: 124
}
function Hero(param) {
this.heroRunning = heroRunning;
this.x = canvasParam.width / 2 - param.width / 2;
this.y = canvasParam.height - param.height * 1.2;
this.width = param.width;
this.height = param.height;
this.index = 0;
this.down = false;
this.num = 0;
this.paint = function() {
ctx.drawImage(this.heroRunning[this.index], this.x, this.y, this.width, this.height);
}
this.sport = function() {
if (!this.down) {
this.num++;
if (this.num % 3 === 0) {
if (this.index === 0) {
this.index = 1;
} else {
this.index = 0;
}
}
} else {
this.index++;
if (this.index === this.heroRunning.length) {
life--;
if (life == 0) {
gamerState = gameOver;
this.index = this.heroRunning.length - 1;
} else {
heroObj = new Hero(heroParam);
}
}
}
}
this.bulletTime = 0;
this.newBullet = function() {
this.bulletTime++;
if (this.bulletTime % 2 === 0) {
bullets.push(new Bullet(bulletParam));
}
}
}
var heroObj = new Hero(heroParam);
canvas.onmousemove = function(e) {
if (gameState === running) {
heroObj.x = e.offsetX - heroObj.width / 2;
heroObj.y = e.offsetY - heroObj.height / 2;
}
}
var bulletImg = new Image();
bulletImg.src = 'img/bullet1.png';
var bulletParam = {
bulletImg: bulletImg,
width: 9,
height: 21
}
function Bullet(param) {
this.bulletImg = param.bulletImg;
this.x = heroObj.x + heroObj.width / 2 - param.width / 2;
this.y = heroObj.y - param.height;
this.width = param.width;
this.height = param.height;
this.paint = function() {
ctx.drawImage(this.bulletImg, this.x, this.y, this.width, this.height);
}
this.down = false;
this.sport = function() {
this.y -= 50;
}
}
var bullets = [];
function bulletsPaint() {
for (var i = 0; i < bullets.length; i++) {
bullets[i].paint();
}
}
function bulletsSport() {
for (var i = 0; i < bullets.length; i++) {
bullets[i].sport();
}
}
function bulletsDelete() {
for (var i = 0; i < bullets.length; i++) {
if (bullets[i].y < -this.height || bullets[i].down) {
bullets.splice(i, 1);
}
}
}
var enemy1Arr = [
'img/enemy1.png',
'img/enemy1_down1.png',
'img/enemy1_down2.png',
'img/enemy1_down3.png',
'img/enemy1_down4.png'
];
var enemy1Img = [];
for (var i = 0; i < enemy1Arr.length; i++) {
enemy1Img[i] = new Image();
enemy1Img[i].src = enemy1Arr[i];
}
var enemy2Arr = [
'img/enemy2.png',
'img/enemy2_down1.png',
'img/enemy2_down2.png',
'img/enemy2_down3.png',
'img/enemy2_down4.png'
];
var enemy2Img = [];
for (var i = 0; i < enemy2Arr.length; i++) {
enemy2Img[i] = new Image();
enemy2Img[i].src = enemy2Arr[i];
}
var enemy3Arr = [
'img/enemy3_n1.png',
'img/enemy3_n2.png',
'img/enemy3_hit.png',
'img/enemy3_down1.png',
'img/enemy3_down2.png',
'img/enemy3_down3.png',
'img/enemy3_down4.png',
'img/enemy3_down5.png',
'img/enemy3_down6.png'
];
var enemy3Img = [];
for (var i = 0; i < enemy3Arr.length; i++) {
enemy3Img[i] = new Image();
enemy3Img[i].src = enemy3Arr[i];
}
var enemy1Param = {
enemyImg: enemy1Img,
width: 57,
height: 51,
life: 3,
score: 1
}
var enemy2Param = {
enemyImg: enemy2Img,
width: 69,
height: 95,
life: 10,
score: 3
}
var enemy3Param = {
enemyImg: enemy3Img,
width: 169,
height: 258,
life: 20,
score: 10
}
function Enemy(param) {
this.enemyImg = param.enemyImg;
this.width = param.width;
this.height = param.height;
this.life = param.life;
this.score = param.score;
this.x = Math.random() * (canvasParam.width - this.width);
this.y = -this.height;
this.index = 0;
this.down = false;
this.bang = false;
this.paint = function() {
ctx.drawImage(this.enemyImg[this.index], this.x, this.y, this.width, this.height);
}
this.sport = function() {
if (!this.down) {
this.y += 3;
} else {
this.life--;
this.down = false;
if (this.life <= 0) {
this.index++;
this.down = true;
if (this.index === this.enemyImg.length) {
this.index = this.enemyImg.length - 1;
this.bang = true;
}
}
}
}
this.hit = function(obj) {
return obj.x + obj.width >= this.x && obj.x <= this.x + this.width &&
obj.y <= this.y + this.height && obj.y + obj.height >= this.y;
}
}
var enemies = [];
function pushEnemy() {
var random = Math.random();
if (random < 0.65) {
enemies.push(new Enemy(enemy1Param));
} else if (random < 0.9) {
enemies.push(new Enemy(enemy2Param));
} else {
enemies.push(new Enemy(enemy3Param));
}
}
function enemyPaint() {
for (var i = 0; i < enemies.length; i++) {
enemies[i].paint();
enemies[i].sport();
}
}
function enemyPaint1() {
for (var i = 0; i < enemies.length; i++) {
enemies[i].paint();
}
}
function enemyDelete() {
for (var i = 0; i < enemies.length; i++) {
if (enemies[i].bang) {
score += enemies[i].score;
}
if (enemies[i].y >= canvasParam.height || enemies[i].bang) {
enemies.splice(i, 1);
}
}
}
function checkHit() {
for (var i = 0; i < enemies.length; i++) {
for (var j = 0; j < bullets.length; j++) {
if (enemies[i].hit(bullets[j])) {
enemies[i].down = true;
bullets[j].down = true;
}
}
if (enemies[i].hit(heroObj)) {
enemies[i].down = true;
heroObj.down = true;
}
}
}
function scoreText() {
ctx.font = '20px bold';
ctx.fillText('得分: ' + score, 20, 30);
ctx.fillText('生命值:' + life, 360, 30)
}
canvas.onmouseout = function() {
if (gameState === running) {
gameState = pause;
}
};
canvas.onmouseover = function() {
if (gameState === pause) {
gameState = running;
}
};
function pausePanit() {
var pauseImg = new Image()
pauseImg.src = "img/game_pause_nor.png";
heroObj.paint();
bulletsPaint();
enemyPaint1();
scoreText();
ctx.drawImage(pauseImg, 220, 420);
}
function gameOverText() {
ctx.font = '50px bold';
ctx.fillText('game over', 120, 420);
ctx.font = '30px bold';
ctx.fillText('点击重新开始', 160, 520);
}
canvas.addEventListener("click", function(e) {
if (gameState === gameOver) {
gameState = ready;
loadingObj.num = 0;
loadingObj.index = 0;
enemies = [];
bullets = [];
life = 3;
score = 0;
heroObj.down = false;
}
});
var enemyNum = 0;
setInterval(function() {
bgObj.paint();
bgObj.sport();
if (gameState === ready) {
ctx.drawImage(logoSrc, 0, 0, 480, 852);
} else if (gameState === loading) {
loadingObj.paint();
loadingObj.sport();
} else if (gameState === running) {
canvas.style.cursor = 'none';
heroObj.paint();
heroObj.sport();
heroObj.newBullet();
bulletsPaint();
bulletsSport();
bulletsDelete();
enemyNum++;
if (enemyNum % 20 === 0) {
pushEnemy();
}
enemyPaint();
checkHit();
enemyDelete();
scoreText();
if (life === 0) {
gameState = gameOver;
}
} else if (gameState === pause) {
pausePanit();
} else if (gameState === gameOver) {
canvas.style.cursor = 'pointer';
gameOverText();
heroObj.paint();
}
}, 60)
</script>
</body>
</html>