Play & Fun Tic Tac Toe
First Selet Your Sign
Here's an example of a Tic Tac Toe game implemented using HTML, CSS, and JavaScript:
HTML (index.html)
Tic Tac Toe with HTML CSS and JS
Play & Fun Tic Tac Toe
First Selet Your Sign
CSS (style.css)
.selection{
padding: 50px 100px;
text-align: center;
border-radius: 12px;
}
.selection h3{
font-size: 3rem;
color: #ff0000;
font-weight: 700;
}
.selection p{
margin-top: 10px;
font-size: 2rem;
color: #333;
}
.selection .players{
width: 100%;
margin-top: 10px;
}
.selection .players .player{
border: 2px solid #ff0000;
border-radius: 8px;
font-size: 2.5rem;
cursor: pointer;
margin: 0 4px;
height: 4rem;
transition: .4s ease;
}
.selection .players .player:hover{
color: whitesmoke;
background-color: #ff0000;
}
.fadeOut{
animation: hide .3s linear alternate;
}
@keyframes hide {
from{
opacity: 1;
transform: scale(1);
}
to{
opacity: 0;
transform: scale(0);
}
}
.fadeIn{
animation: show .3s linear alternate;
}
@keyframes show{
from{
opacity: 0;
transform: scale(0);
}
to{
opacity: 1;
transform: scale(1);
}
}
.play-board{
display: none;
padding: 50px;
border-radius: 8px;
background: whitesmoke;
text-align: center;
}
table td{
width: 5rem;
height: 5rem;
font-size: 2rem;
border-radius: 8px;
border: 2px solid whitesmoke;
background: #000;
cursor: pointer;
transition: .4s linear;
text-align: center;
}
.reset{
cursor: pointer;
padding: 8px 18px;
margin-top: 30px;
color: #fff;
font-size: 1.5rem;
border-radius: 4px;
border: 3px solid #ff0000;
transition: .4s;
}
.reset:hover{
color: whitesmoke;
background: #820000;
}
.winner{
display: none;
padding: 40px 50px;
border-radius: 8px;
background: whitesmoke;
text-align: center;
}
.winner h3{
font-size: 30px;
font-weight: 500;
}
/* Mobile media query */
@media (max-width: 768px) {
.selection h3 {
font-size: 1.7rem;
color: #ff0000;
font-weight: 500;
}
.selection{
padding: 0px 0px;
text-align: center;
border-radius: 12px;
}
.selection p{
margin-top: 10px;
font-size: 1.2rem;
color: #333;
}
}
JS (script.js)
const selection = document.querySelector('.selection');
const playBoard = document.querySelector('.play-board');
const winner = document.querySelector('.winner');
let gameBoard, user='X', computer='O';
const cells = document.querySelectorAll('.cell')
const winCombos =[[0,1,2],[3,4,5],[6,7,8],[0,3,6],[1,4,7],[2,5,8],[0,4,8],[2,4,6]];
const playerSelect = player => {
user=player;
computer = (player === 'X') ? 'O' : 'X';
gameBoard = Array.from(Array(9).keys());
for (let cell of cells){
cell.addEventListener('click',handleClick, false);
}
if (computer === 'X') {
turn(bestSpot(), computer);
}
selection.classList.add('fadeOut')
setTimeout(() => {selection.style.display='none'}, 250);
playBoard.classList.add('fadeIn')
setTimeout(() => {playBoard.style.display='block'}, 250);
}
const startGame = () => {
winner.classList.remove('fadeIn')
winner.classList.add('fadeOut')
setTimeout(() => {winner.style.display= 'none' }, 250);
playBoard.classList.remove('fadeIn')
playBoard.classList.add('fadeOut')
setTimeout(() => {playBoard.style.display= 'none' }, 250);
selection.classList.add('fadeIn')
setTimeout(() => {selection.style.display= 'block' }, 250);
for(let cell of cells){
cell.innerHTML='';
cell.style.color='#fff';
cell.style.background='#000';
}
}
startGame();
const handleClick = gameSpace => {
if (typeof gameBoard[gameSpace.target.id] === 'number') {
turn(gameSpace.target.id, user);
if (!checkWin(gameBoard, user) && !checkTie()) {
setTimeout(() => {turn(bestSpot(), computer)}, 400);
}
}
}
const turn = (spaceId, player) => {
gameBoard[spaceId]=player;
document.getElementById(spaceId).innerHTML= player;
let gameWon = checkWin(gameBoard, player);
if (gameWon) {gameOver(gameWon);}
checkTie();
}
const checkWin=(board, player) => {
let spaces = board.reduce((acc,ele,idx) => (ele === player) ? acc.concat(idx) : acc, []);
let gameWon = null;
for(let [index, winComboSpace] of winCombos.entries()){
if(winComboSpace.every(elem => spaces.indexOf(elem) > -1)){
gameWon = {index : index, player : player}
break;
}
}
return gameWon;
}
const gameOver=gameWon =>{
for(let index of winCombos [gameWon.index]){
document.getElementById(index).style.color='#4E6C50';
document.getElementById(index).style.backgroundColor = '#820000';
}
for (let cell of cells){
cell.removeEventListener('click',handleClick, false);
}
declareWinner(gameWon.player === user ? "You Won The Game" : "Computer Won The Game");
}
const declareWinner = message => {
winner.querySelector('h3').innerHTML=message;
setTimeout(() => {
playBoard.classList.remove('fadeIn')
playBoard.classList.add('fadeOut')
setTimeout(() => {playBoard.style.display='none'}, 250);
winner.classList.add('fadeIn')
setTimeout(() => {winner.style.display='block'}, 250);
}, 1500);
}
const bestSpot = () => {
return minMax (gameBoard, computer).index;
}
const emptySquares = () =>{
return gameBoard.filter((elm, i) => i === elm);
}
const checkTie = () =>{
if (emptySquares().length === 0) {
selection.classList.remove('fadeOut');
for (let cell of cells){
cell.style.backgroundColor='#820000';
cell.removeEventListener('click',handleClick,false);
}
declareWinner("The Game Is Tie!");
return true;
}
return false;
}
const minMax = (testBoard, player) => {
let openSpaces = emptySquares(testBoard);
if (checkWin(testBoard, user))
return{score: -10};
else if (checkWin(testBoard, computer))
return{score: 10};
if (openSpaces.length === 0)
return{score: 0};
let moves = [];
for (let i = 0; i < openSpaces.length; i++){
let move = {};
move.index = testBoard[openSpaces[i]];
testBoard[openSpaces[i]] = player;
if(player === computer)
move.score = minMax(testBoard, user).score;
else
move.score = minMax(testBoard, computer).score;
testBoard[openSpaces[i]]=move.index;
if ((player === computer && move.score === 10) || (player === user && move.score === -10))
return move;
else
moves.push(move);
}
let bestMove, bestScore;
if (player === computer) {
bestScore = -1000;
for (let i = 0; i < moves.length; i++){
if (moves [i].score > bestScore) {
bestScore = moves [i].score;
bestMove = i;
}
}
}
else{
bestScore = 1000;
for (let i = 0; i < moves.length; i++){
if (moves [i].score < bestScore) {
bestScore = moves [i].score;
bestMove = i;
}
}
}
return moves[bestMove];
}