JSFiddle - React, Tailwind, and code Playground
by outis
HTML
<div id="h8">
<div id="board">
<div id="sq0" onclick="move(0)"><div id="xo0"><span class="ex"> </span></div></div>
<div id="sq1" onclick="move(1)"><div id="xo1"><span class="ex"> </span></div></div>
<div id="sq2" onclick="move(2)"><div id="xo2"><span class="ex"> </span></div></div><br/>
<div id="sq3" onclick="move(3)"><div id="xo3"><span class="ex"> </span></div></div>
<div id="sq4" onclick="move(4)"><div id="xo4"><span class="ex"> </span></div></div>
<div id="sq5" onclick="move(5)"><div id="xo5"><span class="ex"> </span></div></div><br/>
<div id="sq6" onclick="move(6)"><div id="xo6"><span class="ex"> </span></div></div>
<div id="sq7" onclick="move(7)"><div id="xo7"><span class="ex"> </span></div></div>
<div id="sq8" onclick="move(8)"><div id="xo8"><span class="ex"> </span></div></div><br/>
</div></div>
<div id="msgX">X Wins</div>
<div id="msgO">O Wins</div>
<div id="h"></div>
<button id="ng" onclick="newgame();">New Game</button>
CSS
html,body{padding:0 0 0 5px;}
#board > div {
cursor: pointer;
}
#board#h8{width:255px;margin:0;padding:0;border:0;}
#sq1,#sq2,#sq3,#sq4,#sq5,#sq6,#sq7,#sq8,#sq9{width:80px;height:80px;:inline-block;border:2px solid black;display:inline-block;
background: linear-gradient(to bottom, #444 0%, #111 100%);}
#xo1,#xo2,#xo3,#xo4,#xo5,#xo6,#xo7,#xo8,#xo9{padding:0 0 0 16px;color:#fff;font:700 60px Arial,sans-serif;display:inline-block;}
.oh{font-size:66px;color:#ff0;}
.ex{font-size:66px;color:#f0f;}
button{color:#fff;width:251px;background: linear-gradient(to bottom, rgba(0,0,255,1) 0%, rgba(0,0,64,1) 100%);}
#prefetch{display:none;}
#h8{opacity:1;}
#msg8,#msg64{display:none;width:250px;text-align:center;font:700 40px Arial,sans-derif;color:#f00;}
#ng{font:700 33px Arial,sans-serif;}
JavaScript
(function () {
const xo = [null,null,null,null,null,null,null,null,null,null],
// bitmasks for lines of squares
lines = [
0b000000000000111111,
0b000000111111000000,
0b111111000000000000,
0b000011000011000011,
0b001100001100001100,
0b110000110000110000,
0b110000001100000011,
0b000011001100110000,
],
// which line each square participates in; indexes into lines
participation = [
[0, 3, 6],
[0, 4],
[0, 5, 7],
[1, 3],
[1, 4, 6, 7],
[1, 5],
[2, 3, 7],
[2, 4],
[2, 5, 6],
],
wins = {
0b000000000000010101: 0,
0b000000000000101010: 1,
0b000000010101000000: 0,
0b000000101010000000: 1,
0b010101000000000000: 0,
0b101010000000000000: 1,
0b000001000001000001: 0,
0b000010000010000010: 1,
0b000100000100000100: 0,
0b001000001000001000: 1,
0b010000010000010000: 0,
0b100000100000100000: 1,
0b010000000100000001: 0,
0b100000001000000010: 1,
0b000001000100010000: 0,
0b000010001000100000: 1,
},
h = {
0: document.getElementById('h8'),
1: document.getElementById('h8'),
2: document.getElementById('h'),
},
msg = {
0: document.getElementById('msgX'),
1: document.getElementById('msgO'),
2: document.getElementById('h'),
},
img = ['<span class="ex">X</span>','<span class="oh">Ο</span>','<span class="ex"> </span>'];
for (let i = 0; i < xo.length; ++i) {
xo[i] = document.getElementById('xo' + i);
}
var player = 0,
board = 0x0;
function win(id) {
for (let line of participation[id]) {
line = lines[line] & board;
if (line in wins) {
return wins[line];
}
}
return 2;
}
function square(id) {
return 0x3 & (board >> (id * 2));
}
function setSquare(id, val) {
board |= ((val & 0x3) << (id * 2));
}
function move(id) {
let prev = square(id),
empty = ! prev;
setSquare(id, prev || (player...