Home
Tutorial
JavaScript Games
Sudoku Puzzle Game using JavaScript
Online HTML Editor : Sudoku Game with JavaScript
Run Output
Output Rosolution:
<!DOCTYPE html> <html lang="en"> <head> <!-- for delete icon --> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css"> <meta name="viewport" content="width=device-width, initial-scale=1"> <style> html, body, div, span, applet, object, iframe, h1, h2, h3, h4, h5, h6, p, blockquote, pre, a, abbr, acronym, address, big, cite, code, del, dfn, em, img, ins, kbd, q, s, samp, small, strike, strong, sub, sup, tt, var, b, u, i, center, dl, dt, dd, ol, ul, li, fieldset, form, label, legend, table, caption, tbody, tfoot, thead, tr, th, td, article, aside, canvas, details, embed, figure, figcaption, footer, header, hgroup, menu, nav, output, ruby, section, summary, time, mark, audio, video { margin: 0; padding: 0; } /* font style cdn link */ @import url('https://fonts.googleapis.com/css2?family=Anton&family=Roboto:wght@100;400;700&family=Rubik+Bubbles&display=swap'); *{ box-sizing: border-box; } body{ font-family: 'Anton', sans-serif; } .container{ height: 100vh; width: 100%; text-align: center; } .container h1{ font-size: 40px; padding-top: 20px; } .container .mistake{ background: rgb(76,204,255); padding: 10px; width: 60vmin; font-size: 24px; margin: 20px auto; color: #fff; border-radius: 10px; border: 2px solid #000; } #gameBoard{ height: 60vmin; width: 60vmin; background: #fff; margin: 0 auto; display: flex; flex-wrap: wrap; border: 3px solid #000; } .tile{ height: calc(100% / 9); width: calc(100% / 9); border: 1px solid #ccc; font-size: 30px; display: flex; justify-content: center; align-items: center; background: #fff; } .filled{ background: #f2f2f2; } .select-tile{ background: rgba(76,204,255, 0.5); } #digits{ width: 60vmin; display: flex; margin: 20px auto; } #digits .tile{ background: rgb(76,204,255); border-radius: 10px; border: 1px solid #000; color: #fff; cursor: pointer; } .border-right{ border-right: 2px solid #000; } .border-bottom{ border-bottom: 2px solid #000; } #delete{ color: #f00; font-size: 30px; cursor: pointer; } .danger{ color: #f00; } @media (max-width:600px) { .tile{ font-size: 18px; } } @media (max-width:400px) { .tile{ font-size: 16px; } } </style> </head> <body> <div class="container"> <h1>Sudoku</h1> <div class="mistake">Mistake: <span id="mistake">0</span>/3</div> <div id="gameBoard"></div> <div id="digits"></div> <div id="delete"> <i class="fa fa-trash"></i> </div> </div> <script> const gameBoard = document.querySelector("#gameBoard"); const digits = document.querySelector("#digits"); const deleteNum = document.querySelector("#delete"); const mistake = document.querySelector("#mistake"); let lastSelected = null; let error = 0; //puzzle const puzzle = [ "8-6-1----", "--3-64-9-", "9-----816", "-8-396---", "7-2-4-3-9", "---572-8-", "521-----4", "-3-75-2--", "----2-1-5", ]; //puzzle solution const solution = [ "856917423", "213864597", "947235816", "185396724", "762148359", "394572681", "521683974", "439751268", "678429135", ]; //when window load puzzle create window.onload = (() => { for (let i = 0; i < 9; i++) { for (let j = 0; j < 9; j++) { const div = document.createElement("div"); div.classList.add("tile"); div.addEventListener("click", selectTile); div.setAttribute("row", i); div.setAttribute("col", j); if (puzzle[i][j] != "-") { div.innerText = puzzle[i][j]; div.classList.add("filled"); } if (i == 2 || i == 5) { div.classList.add("border-bottom"); } if (j == 2 || j == 5) { div.classList.add("border-right"); } gameBoard.appendChild(div); } } // creating digits for (let i = 0; i < 9; i++) { const div = document.createElement("div"); div.classList.add("tile"); div.addEventListener("click", addNumber); div.innerText = i + 1; div.style.height = gameBoard.querySelector(".tile").clientHeight + "px"; digits.appendChild(div); } }); //select Tile function selectTile() { if (lastSelected != null) { lastSelected.classList.remove("select-tile"); } lastSelected = this; lastSelected.classList.add("select-tile"); } //add digits (0-9) to Tile function addNumber() { if (lastSelected.innerText == "" || lastSelected.classList.contains("danger")) { lastSelected.innerText = this.innerText; } let row = lastSelected.getAttribute("row"); let col = lastSelected.getAttribute("col"); if (solution[row][col] == lastSelected.innerText) { lastSelected.classList.remove("danger"); } else { lastSelected.classList.add("danger"); addErrorandDisplay(); } if (error > 2) { alert("You Lost!"); location.reload(); } if (isAllTilesFilled()) { const allTiles = gameBoard.querySelectorAll(".tile"); let userAnswer = [...allTiles].map((tile) => { return tile.innerText; }); let num = 0; for (let i = 0; i < 9; i++) { for (let j = 0; j < 9; j++) { if (solution[i][j] != userAnswer[num]) { allTiles[num].classList.add("danger"); } num++ } } let dangerClass = [...allTiles].some((tile) => { return tile.classList.contains("danger"); }); if (dangerClass) { if (error > 2) { alert("you lost!"); location.reload(); } } else { alert("Congratuations! You win the puzzle!"); } } } //delete number of Tile deleteNum.onclick = () => { if (!lastSelected.classList.contains("filled")) { lastSelected.innerText = ""; } } //check again any wrong numbers in any tile function addErrorandDisplay() { error++; mistake.innerText = error; } //check all tiles filled or not function isAllTilesFilled() { const allTiles = gameBoard.querySelectorAll(".tile"); return [...allTiles].every((tile) => { return tile.innerText != ""; }); } </script> </body> </html>