🎮 Games
Score0
CategoryClassic
Plays67k plays
Gamelot
The Kingdom of Games
🤖
Tictactoe Ai
Tic-Tac-Toe against an unbeatable AI. The AI uses the minimax algorithm — it wil…
Free · No sign-up · Instant play
CLICK Click any empty square to play
Tictactoe Ai
Tic-Tac-Toe against an unbeatable AI. The AI uses the minimax algorithm — it wil…
Free · No sign-up · Instant play
TAPClick any empty square to play
😊 Easy
🤔 Medium
💀 Impossible
You (X)
0
Draw
0
AI (O)
0
Your turn — you're X
AI is thinking...
You are X, the AI is O. Easy makes mistakes. Medium plays well. Impossible uses Minimax — it literally cannot lose.
Advertisement /* ══════════════════════════════════════ GAMELOT — TIC-TAC-TOE AI Minimax algorithm for unbeatable AI 3 difficulty levels ══════════════════════════════════════ */ const WINS = [[0,1,2],[3,4,5],[6,7,8],[0,3,6],[1,4,7],[2,5,8],[0,4,8],[2,4,6]]; let board, gameOver, playerTurn, difficulty, scores; difficulty = 'medium'; scores = {x:0,o:0,d:0}; function init() { board = Array(9).fill(null); gameOver = false; playerTurn = true; updateBoard(); setStatus("Your turn — you're X"); } function setDiff(d, el) { difficulty = d; document.querySelectorAll('.diff-btn').forEach(b=>b.classList.remove('active')); el.classList.add('active'); resetGame(); } function play(idx) { if(!playerTurn || gameOver || board[idx]) return; board[idx] = 'X'; updateBoard(); const result = checkWin(board); if(result) { endGame(result); return; } if(board.every(c=>c)) { endGame('draw'); return; } playerTurn = false; setStatus('AI is thinking...'); document.getElementById('thinking').classList.add('show'); setTimeout(aiMove, difficulty==='easy'?200:400); } function aiMove() { document.getElementById('thinking').classList.remove('show'); let idx; if(difficulty==='easy') idx = easyMove(); else if(difficulty==='medium') idx = mediumMove(); else idx = bestMove(); if(idx===null) return; board[idx]='O'; updateBoard(); const result=checkWin(board); if(result){endGame(result);return;} if(board.every(c=>c)){endGame('draw');return;} playerTurn=true; setStatus("Your turn — you're X"); } // Easy: mostly random with occasional smart move function easyMove() { const empty=board.map((v,i)=>v?null:i).filter(v=>v!==null); if(Math.random()<0.3) return mediumMove(); return empty[Math.floor(Math.random()*empty.length)]??null; } // Medium: win/block, otherwise random function mediumMove() { // Win if possible for(const w of WINS){const [a,b,c]=w;if(board[a]==='O'&&board[b]==='O'&&!board[c])return c;if(board[a]==='O'&&!board[b]&&board[c]==='O')return b;if(!board[a]&&board[b]==='O'&&board[c]==='O')return a;} // Block player for(const w of WINS){const [a,b,c]=w;if(board[a]==='X'&&board[b]==='X'&&!board[c])return c;if(board[a]==='X'&&!board[b]&&board[c]==='X')return b;if(!board[a]&&board[b]==='X'&&board[c]==='X')return a;} // Centre if(!board[4]) return 4; // Random const empty=board.map((v,i)=>v?null:i).filter(v=>v!==null); return empty[Math.floor(Math.random()*empty.length)]??null; } // Hard: full minimax function bestMove() { let best=-Infinity,idx=null; board.forEach((v,i)=>{ if(v) return; board[i]='O'; const score=minimax(board,0,false,-Infinity,Infinity); board[i]=null; if(score>best){best=score;idx=i;} }); return idx; } function minimax(b,depth,isMax,alpha,beta) { const r=checkWin(b); if(r==='O') return 10-depth; if(r==='X') return depth-10; if(b.every(c=>c)) return 0; if(isMax) { let best=-Infinity; for(let i=0;i<9;i++){ if(b[i]) continue; b[i]='O'; best=Math.max(best,minimax(b,depth+1,false,alpha,beta)); b[i]=null; alpha=Math.max(alpha,best); if(beta<=alpha) break; } return best; } else { let best=Infinity; for(let i=0;i<9;i++){ if(b[i]) continue; b[i]='X'; best=Math.min(best,minimax(b,depth+1,true,alpha,beta)); b[i]=null; beta=Math.min(beta,best); if(beta<=alpha) break; } return best; } } function checkWin(b) { for(const [a,bp,c] of WINS){ if(b[a]&&b[a]===b[bp]&&b[a]===b[c]) return b[a]; } return null; } function getWinLine(b) { for(const line of WINS){ const [a,bp,c]=line; if(b[a]&&b[a]===b[bp]&&b[a]===b[c]) return line; } return null; } function endGame(result) { gameOver=true; const winLine=getWinLine(board); if(winLine) winLine.forEach(i=>document.getElementById('c'+i).classList.add('win')); if(result==='X'){scores.x++;setStatus('🎉 You win!');} else if(result==='O'){scores.o++;setStatus('🤖 AI wins!');} else{scores.d++;setStatus("🤝 It's a draw!");} document.getElementById('score-x').textContent=scores.x; document.getElementById('score-o').textContent=scores.o; document.getElementById('score-d').textContent=scores.d; } function updateBoard() { board.forEach((v,i)=>{ const cell=document.getElementById('c'+i); cell.textContent=v||''; cell.className='cell'+(v?' taken '+v.toLowerCase():''); }); } function setStatus(msg){document.getElementById('status').textContent=msg;} function resetGame(){ document.getElementById('thinking').classList.remove('show'); init(); } window.addEventListener('DOMContentLoaded',init); function showControlsHint() { var el = document.getElementById('gl-hint-tictactoeai'); if (!el) return; el.style.animation = 'none'; void el.offsetWidth; el.style.animation = 'hintFadeIn .4s ease both, hintFadeOut .4s ease 4s forwards'; }
Classic · Tictactoe Ai
Advertisement
🤖
Tictactoe Ai
★ 4.6 Classic 67k plays
Tic-Tac-Toe against an unbeatable AI. The AI uses the minimax algorithm — it will never lose. Can you force a draw?
Click any empty square to play The AI plays perfectly — can you draw?
WhatsApp
Similar games
Advertisement
Advertisement