贪吃蛇游戏
贪吃蛇是一款经典的休闲益智游戏。本文将通过HTML5和JavaScript详细解析如何实现一个简易版的贪吃蛇游戏。游戏的主要逻辑包括蛇的移动、碰撞检测、食物生成等功能。以下是游戏的完整代码及注释解析。(纯属好玩)
运行效果
注意
PC端可以用键盘上,下,左,右键操作,手机上可以用按钮操作。
代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Snake Game</title>
<style>
body {
margin: 0;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
height: 100vh;
background-color: #000;
}
canvas {
border: 1px solid #fff;
}
.mobile-controls {
display: flex;
justify-content: center;
margin-top: 20px;
}
.control-button {
background-color: #fff;
border: 1px solid #000;
padding: 10px 20px;
margin: 5px;
font-size: 18px;
cursor: pointer;
border-radius: 5px;
}
</style>
</head>
<body>
<canvas id="gameCanvas"></canvas>
<div class="mobile-controls">
<button class="control-button" id="left">左</button>
<button class="control-button" id="up">上</button>
<button class="control-button" id="down">下</button>
<button class="control-button" id="right">右</button>
</div>
<script>
const canvas = document.getElementById('gameCanvas');
const ctx = canvas.getContext('2d');
const scale = 20;
const rows = 20;
const columns = 20;
canvas.width = columns * scale;
canvas.height = rows * scale;
let snake;
let food;
let direction = { x: 1, y: 0 };
let isGameOver = false;
let baseSnakeColor;
let foodColor;
// 随机生成颜色的函数
function getRandomColor() {
const r = Math.floor(Math.random() * 256);
const g = Math.floor(Math.random() * 256);
const b = Math.floor(Math.random() * 256);
return `rgb(${r}, ${g}, ${b})`;
}
function Snake() {
this.body = [{ x: 10, y: 10 }];
this.draw = function () {
for (let i = 0; i < this.body.length; i++) {
const gradientFactor = i / this.body.length;
// 通过调整颜色实现渐变效果,头部颜色较深,尾部颜色较浅
const r = Math.floor(255 * (1 - gradientFactor)); // 以红色基调为例
const g = Math.floor(100 * gradientFactor); // 可根据需要调整
const b = Math.floor(150); // 固定一个蓝色调
ctx.fillStyle = `rgb(${r},${g},${b})`;
ctx.fillRect(this.body[i].x * scale, this.body[i].y * scale, scale, scale);
}
};
this.update = function () {
const newHead = {
x: this.body[0].x + direction.x,
y: this.body[0].y + direction.y
};
// 检查蛇是否撞墙或与自身碰撞
if (newHead.x < 0 || newHead.x >= columns || newHead.y < 0 || newHead.y >= rows || this.isCollision(newHead)) {
isGameOver = true;
}
this.body.unshift(newHead);
if (newHead.x === food.x && newHead.y === food.y) {
generateFood();
} else {
this.body.pop();
}
};
// 检查蛇是否与自身碰撞
this.isCollision = function (pos) {
for (let i = 0; i < this.body.length; i++) {
if (this.body[i].x === pos.x && this.body[i].y === pos.y) {
return true;
}
}
return false;
};
}
// 生成食物,确保食物不会生成在蛇身体上
function generateFood() {
let isOnSnake;
do {
isOnSnake = false;
food = {
x: Math.floor(Math.random() * columns),
y: Math.floor(Math.random() * rows)
};
// 检查食物是否生成在蛇身体上
for (let i = 0; i < snake.body.length; i++) {
if (snake.body[i].x === food.x && snake.body[i].y === food.y) {
isOnSnake = true;
break;
}
}
} while (isOnSnake); // 如果食物生成在蛇身体上,重新生成
foodColor = getRandomColor(); // 每次生成新的食物时,食物颜色变化
}
// 绘制食物
function drawFood() {
ctx.fillStyle = foodColor;
ctx.fillRect(food.x * scale, food.y * scale, scale, scale);
}
// 游戏主循环
function gameLoop() {
if (isGameOver) {
alert('Game Over');
document.location.reload();
return;
}
ctx.clearRect(0, 0, canvas.width, canvas.height);
snake.update();
snake.draw();
drawFood();
setTimeout(gameLoop, 200); // 控制游戏速度(200ms 间隔)
}
// 控制蛇的方向
window.addEventListener('keydown', (e) => {
switch (e.key) {
case 'ArrowUp':
if (direction.y === 0) direction = { x: 0, y: -1 };
break;
case 'ArrowDown':
if (direction.y === 0) direction = { x: 0, y: 1 };
break;
case 'ArrowLeft':
if (direction.x === 0) direction = { x: -1, y: 0 };
break;
case 'ArrowRight':
if (direction.x === 0) direction = { x: 1, y: 0 };
break;
}
});
// 移动端控制按钮
document.getElementById('left').addEventListener('click', () => {
if (direction.x === 0) direction = { x: -1, y: 0 };
});
document.getElementById('right').addEventListener('click', () => {
if (direction.x === 0) direction = { x: 1, y: 0 };
});
document.getElementById('up').addEventListener('click', () => {
if (direction.y === 0) direction = { x: 0, y: -1 };
});
document.getElementById('down').addEventListener('click', () => {
if (direction.y === 0) direction = { x: 0, y: 1 };
});
// 初始化游戏
baseSnakeColor = getRandomColor(); // 在游戏开始时生成蛇的基色,并且保持一致
snake = new Snake();
generateFood();
gameLoop();
</script>
</body>
</html>