-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathgame_of_life.html
140 lines (121 loc) · 4.11 KB
/
game_of_life.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
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
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Game of Life</title>
</head>
<body>
<div style="text-align: center;">
<canvas id="canvas" width="600" height="400"></canvas>
</div>
<script>
/**
* Game of Life in plain Javascript
* Based on John Conway's Game of Life
*
* Author: Carlos E. Torres
* E-mail: cetorres@cetorres.com
* Github: https://github.com/cetorres
*/
let canvas;
let canvasContext;
let grid;
let cols;
let rows;
let resolution = 10;
let bgColor = "black";
let cellColor = "black";
let liveCellColor = "white";
let strokeColor = "black";
let gameSpeed = 50;
window.onload = function () {
// Define game canvas
canvas = document.getElementById("canvas");
canvasContext = canvas.getContext("2d");
// Initialize game
initGame();
gameLoop();
// Start game loop
setInterval(gameLoop, gameSpeed);
}
function initGame() {
// Draw background
canvasContext.fillStyle = bgColor;
canvasContext.fillRect(0, 0, canvas.width, canvas.height);
// Create cols and rows dynamically accordingly to the resolution
cols = canvas.width / resolution;
rows = canvas.height / resolution;
// Create grid
grid = make2DArray(cols, rows);
// Randomly fill the grid with 0s and 1s
for (let i = 0; i < cols; i++) {
for (let j = 0; j < rows; j++) {
grid[i][j] = Math.floor(Math.random() * 2);
}
}
}
function gameLoop() {
let next = make2DArray(cols, rows);
for (let i = 0; i < cols; i++) {
for (let j = 0; j < rows; j++) {
let state = grid[i][j];
// Count live neighbors
let neighbors = countNeighbors(grid, i, j);
// Rules
if (state == 0 && neighbors == 3) {
next[i][j] = 1;
} else if (state == 1 && (neighbors < 2 || neighbors > 3)) {
next[i][j] = 0;
} else {
next[i][j] = state;
}
}
}
grid = next;
for (let i = 0; i < cols; i++) {
for (let j = 0; j < rows; j++) {
let x = i * resolution;
let y = j * resolution;
let color = cellColor;
if (grid[i][j] == 1) {
color = liveCellColor;
}
rect(x, y, resolution, resolution, color, strokeColor);
}
}
}
//
// Util functions
//
// Make a 2D array
function make2DArray(cols, rows) {
let arr = new Array(cols);
for (let i = 0; i < arr.length; i++) {
arr[i] = new Array(rows);
}
return arr;
}
// Count the live neighbors around x, y
function countNeighbors(grid, x, y) {
let sum = 0;
for (let i = -1; i < 2; i++) {
for (let j = -1; j < 2; j++) {
let col = (x + i + cols) % cols;
let row = (y + j + rows) % rows;
sum += grid[col][row];
}
}
// Remote itself from the sum
sum -= grid[x][y];
return sum;
}
// Draw a filled rectangle with stroke border
function rect(x, y, w, h, fillColor = "white", strokeColor = "black") {
canvasContext.fillStyle = fillColor;
canvasContext.fillRect(x, y, w, h);
canvasContext.strokeStyle = strokeColor;
canvasContext.strokeRect(x, y, w, h);
}
</script>
</body>
</html>