Created
June 13, 2016 20:09
-
-
Save lostmahbles/8fa28c5464a122c39cb0997364e8de52 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<html> | |
<head> | |
<script type="text/javascript"> | |
// | |
// Game variables | |
// | |
var boardSize = 10; // Number of cells on each side of board | |
var refreshRateHz = 2; // Refresh rate in Hz. i.e 2 = every half second | |
var board = []; // state | |
var headX, headY; // position of the head of the snake | |
var tailX, tailY; // position of the tail of the snake | |
var direction; // current direction of the snake | |
var isGameOver; // tail recursion flag | |
var score; // current score ~ number of cells in the snake | |
// | |
// Set true to see cell numbers | |
// | |
var debug = false; | |
// | |
// Set the board state. | |
// | |
var initializeBoard = function() { | |
board = []; | |
headX = boardSize/2; | |
headY = boardSize/2; | |
tailX = headX; | |
tailY = headY; | |
direction = "right"; | |
isGameOver = false; | |
score = 0; | |
// initialize table | |
for(x = 0; x < boardSize; x++) { | |
board[x] = []; | |
for(y = 0; y < boardSize; y++) { | |
board[x][y] = "none"; | |
} | |
} | |
// initializing snake | |
board[headX][headY] = direction; | |
// initialize target | |
generateTarget(); | |
// Set the initial score. | |
updateScore(); | |
} | |
// | |
// Randomly add a target to the board | |
// | |
var generateTarget = function() { | |
var targetX, targetY; | |
// | |
// Generate the target, and regenerate if it | |
// was going to fall on the snake | |
// | |
do { | |
targetX = getRandomInt(0, boardSize - 1); | |
targetY = getRandomInt(0, boardSize - 1); | |
} while(board[targetX][targetY] != "none") | |
board[targetX][targetY] = "target"; | |
} | |
// from http://stackoverflow.com/questions/1527803/generating-random-whole-numbers-in-javascript-in-a-specific-range | |
function getRandomInt(min, max) { | |
return Math.floor(Math.random() * (max - min + 1)) + min; | |
} | |
// | |
// Render the board based on the board state | |
// | |
var drawBoard = function() { | |
var table = document.getElementById("board"); | |
table.innerHTML = ""; | |
for(y = boardSize - 1; y >= 0; y--) { | |
row = table.insertRow(0); | |
for(x = boardSize - 1; x >= 0; x--) { | |
cell = row.insertCell(0); | |
cell.setAttribute('class', board[x][y]) | |
if (debug) { | |
cell.innerHTML = "["+x+","+y+"]" | |
} | |
} | |
} | |
} | |
var moveSnake = function() { | |
// move head | |
switch(direction) { | |
case "up": | |
headY--; | |
break; | |
case "down": | |
headY++; | |
break; | |
case "left": | |
headX--; | |
break; | |
case "right": | |
headX++; | |
break; | |
} | |
moveTail = true; | |
// Game Over if snake hits wall. | |
if (headX < 0 || headX == boardSize || | |
headY < 0 || headY == boardSize) { | |
gameOver(); | |
return; | |
} | |
if (board[headX][headY] == "target") { | |
generateTarget(); | |
updateScore(); | |
moveTail = false; | |
} else if (board[headX][headY] != "none") { | |
// We hit the snake. Game over. | |
gameOver(); | |
return; | |
} | |
// Update the direction of the head cell. | |
board[headX][headY] = direction; | |
if (moveTail) { | |
// remove tail | |
tailDirection = board[tailX][tailY]; | |
board[tailX][tailY] = "none"; | |
// Set a new tail based on last tail's direction. | |
switch(tailDirection) { | |
case "up": | |
tailY--; | |
break; | |
case "down": | |
tailY++; | |
break; | |
case "left": | |
tailX--; | |
break; | |
case "right": | |
tailX++; | |
break; | |
} | |
} | |
if (debug) { | |
console.log("head: " + headX + ", " + headY); | |
console.log("tail: " + tailX + ", " + tailY); | |
} | |
} | |
var updateScore = function() { | |
score++; | |
document.getElementById("score").innerHTML = score; | |
} | |
var gameOver = function() { | |
isGameOver = true; | |
alert("Game Over! Your final score was " + score + "."); | |
} | |
var refreshLoop = function() { | |
moveSnake(); | |
drawBoard(); | |
if(!isGameOver){ | |
window.setTimeout(refreshLoop, 1000/refreshRateHz); | |
} | |
} | |
var startGame = function() { | |
initializeBoard(); | |
refreshLoop(); | |
} | |
window.addEventListener("keydown", function(e) { | |
// Set the snake's current direction w/ arrow | |
// key presses. | |
switch(e.keyCode) { | |
case 38: | |
direction = "up"; | |
break; | |
case 40: | |
direction = "down"; | |
break; | |
case 37: | |
direction = "left"; | |
break; | |
case 39: | |
direction = "right"; | |
break; | |
} | |
board[headX][headY] = direction; | |
}) | |
</script> | |
</head> | |
<body> | |
<style> | |
button { | |
margin-bottom: 20px; | |
} | |
table { | |
border-collapse: collapse; | |
} | |
table#board > tbody > tr > td.target { | |
background: red; | |
} | |
table#board > tbody > tr > td.up, | |
table#board > tbody > tr > td.down, | |
table#board > tbody > tr > td.left, | |
table#board > tbody > tr > td.right { | |
background: #666666; | |
} | |
table > tbody > tr > td { | |
border: 1px solid #efefef; | |
padding: 10px; | |
background: #dedede; | |
} | |
</style> | |
<button onclick="startGame()">Start Game!</button> | |
<table id="board"></table> | |
<h1>Your score: <span id="score">0</span></h1> | |
</body> | |
</html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment