<nav class="app-bar">
  <button onclick="HamburgerButtonClick();" class="button bar-button hamburger-button">
    <span class="material-icons">menu</span>
  </button>
  <div class="bar-font title">Sudoku</div>
  <div id="moreoption-sec" class="more-option-div more-button">
    <button onclick="moreOptionButtonClick()" class="button bar-button">
      <span class="material-icons">more_vert</span>
    </button>
    <!-- it is important to put these styles in here because if I do not do that it will not work in javaScript-->
    <div id="more-option-list" style="visibility: hidden;max-height: 10px;max-width: 40px;min-width: 40px;" class="more-option-list">
      <button onclick="hintButtonClick()" ripple-color="#003c8f" class="button nav-item vertical-adjust">Hint</button>
      <button onclick="restartButtonClick()" ripple-color="#003c8f" class="button nav-item vertical-adjust">Restart</button>
      <button onclick="SurrenderButtonClick()" ripple-color="tomato" class="button nav-item vertical-adjust">Surrender</button>
    </div>
  </div>

  <button id="pause-btn" onclick="pauseGameButtonClick()" class="button bar-button more-button">
    <span id="pause-icon" class="material-icons">pause</span>
    <span id="pause-text">Pause</span>
  </button>
  <button id="check-btn" onclick="checkButtonClick()" class="button bar-button more-button">
    <span class="material-icons">done_all</span>
    <span>Check</span>
  </button>
  <button id="isunique-btn" style="display: none;" onclick="isUniqueButtonClick();" class="button bar-button more-button">
    <span class="material-icons">call_split</span>
    <span>Is unique</span>
  </button>
  <button id="solve-btn" style="display: none;" onclick="solveButtonClick()" class="button bar-button more-button">
    <span class="material-icons">border_color</span>
    <span>Solve</span>
  </button>

</nav>

<div id="hamburger-menu" class="hamburger-menu">
  <nav id="nav-menu" class="nav-menu">
    <div class="nav-head">
      <div class="nav-head-img">
        <img src="https://image.ibb.co/jmuOKn/icon.jpg" art="" />
      </div>
      <div class="nav-head-title">Sudoku</div>
    </div>
    <ul class="nav-items">
      <button onclick="showDialogClick('dialog');" ripple-color="#003c8f" class="button nav-item vertical-adjust">
        <div>
          <span class="material-icons">add</span>
          <span style="left:12px;">New game</span>
        </div>
      </button>
      <button onclick="sudokuSolverMenuClick();" ripple-color="#003c8f" class="button nav-item vertical-adjust">
        <div>
          <span class="material-icons">edit</span>
          <span style="left:12px;">Sudoku Solver</span>
        </div>
      </button>
      <button onclick="showDialogClick('about-dialog');" ripple-color="#003c8f" class="button nav-item vertical-adjust">
        <div>
          <span class="material-icons">star</span>
          <span style="left:12px;">About</span>
        </div>
      </button>
      <div class="bar-footer">
        <ul>
          <a href="#" class="bar-footer-link">Site feedback</a>
          <a href="#" class="bar-footer-link">Privacy</a>
          <a href="#" class="bar-footer-link">Terms</a>
        </ul>
      </div>
    </ul>
  </nav>
  <div class="nav-menu-blank" onclick="hideHamburgerClick()">

  </div>
</div>

<div class="floating">
  <button onclick="showDialogClick('dialog');" class="button floating-btn vertical-adjust">
    <span class="material-icons">add</span>
  </button>
</div>

<div id="dialog" class="dialog">
  <div id="dialog-box" class="dialog-content">
    <div class="dialog-header">New game</div>

    <div class="dialog-body">
      <p>Select game difficulty to get started.</p>
      <ul>
        <li class="radio-option">
          <label for="very-easy">
            <input id="very-easy" value="very easy" type="radio" name="difficulty"> Very easy
          </label>
        </li>
        <li class="radio-option">
          <label for="easy">
            <input id="easy" value="easy" type="radio" name="difficulty"> Easy
          </label>
        </li>
        <li class="radio-option">
          <label for="normal">
            <input id="normal" value="normal" type="radio" name="difficulty"> Normal
          </label>
        </li>
        <li class="radio-option">
          <label for="hard">
            <input id="hard" value="hard" type="radio" name="difficulty"> Hard
          </label>
        </li>
        <li class="radio-option">
          <label for="very-hard">
            <input id="very-hard" value="expert" type="radio" name="difficulty"> Expert
          </label>
        </li>
      </ul>
    </div>

    <div class="dialog-footer">
      <button onclick="startGameButtonClick();" ripple-color="#003c8f" class="button dialog-btn vertical-adjust">OK</button>
      <button onclick="hideDialogButtonClick('dialog');" ripple-color="#202020" class="button dialog-btn vertical-adjust">Cancel</button>
    </div>
  </div>
</div>

<div id="about-dialog" class="dialog">

  <div id="about-dialog-box" onblur="hideDialogButtonClick('about-dialog');" class="dialog-content about-dialog-content">
    <div class="dialog-header">CodeTeam6</div>

    <div class="dialog-body">
      <p>about us</p>
      <div class="card-group">
        <div class="card dialog-card">
          <div class="about-card-img">
            <img src="https://image.ibb.co/crYHen/a_abdallah.jpg" alt="" />
          </div>
          <div class="about-card-title">Ahmad Abdalla</div>
          <div class="about-card-content">Egypt</div>
          <div class="about-card-quote">My dream is to be the best developer in the world, and I'll work continuously to achieve that.</div>
        </div>
        <div class="card dialog-card">
          <div class="about-card-img">
            <img src="https://image.ibb.co/mKg3Kn/a_alrifai.jpg" alt="" />
          </div>
          <div class="about-card-title">Ayman Alrifai</div>
          <div class="about-card-content">Libya</div>
          <div class="about-card-quote">I love coding & design. I learn every day to build awesome stuff.</div>
        </div>
        <div class="card dialog-card">
          <div class="about-card-img">
            <img src="https://image.ibb.co/dYd5X7/m_diab.jpg" alt="" />
          </div>
          <div class="about-card-title">Mohammad Diab</div>
          <div class="about-card-content">Syria</div>
          <div class="about-card-quote">Silent but deadly.</div>
        </div>
        <div class="card dialog-card">
          <div class="about-card-img">
            <img src="https://image.ibb.co/g01g5S/" alt="" />
          </div>
          <div class="about-card-title">RB</div>
          <div class="about-card-content">Palestine</div>
          <div class="about-card-quote">I think outside the box, I love trying everything new.</div>
        </div>

      </div>
    </div>

    <div class="dialog-footer">
      <button onclick="hideDialogButtonClick('about-dialog');" ripple-color="#003c8f" class="button dialog-btn vertical-adjust">OK</button>
    </div>
  </div>
</div>

<div class="body" id="sudoku">
  <div class="card game">
    <table id="puzzle-grid">
      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

      <tr>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>

        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
        <td>
          <input type="text" maxlength="1" onchange="checkInput(this)" disabled />
        </td>
      </tr>

    </table>
  </div>

  <div class="card status">
    <div id="game-number">game #0</div>
    <ul class="game-status">
      <li>
        <div class="vertical-adjust">
          <span class="material-icons">timer</span>
          <span id="timer-label">Time</span>
        </div>
        <div id="timer" class="timer">00:00</div>
      </li>

      <li>
        <div class="vertical-adjust">
          <span class="material-icons">network_check</span>
          <span id="game-difficulty-label">Game difficulty</span>
        </div>
        <div id="game-difficulty" class="timer">undefined</div>
      </li>
      <li>
        <div class="vertical-adjust">
          <span class="material-icons">grid_on</span>
          <span>Remaining numbers</span>
        </div>
        <div class="remain-table">
          <div class="remain-column">
            <div class="remain-cell">
              <div class="remain-cell-header">1</div>
              <div onchange="document.write('Hello');" id="remain-1" class="remain-cell-content">0</div>
            </div>
            <div class="remain-cell">
              <div class="remain-cell-header">4</div>
              <div id="remain-4" class="remain-cell-content">0</div>
            </div>
            <div class="remain-cell">
              <div class="remain-cell-header">7</div>
              <div id="remain-7" class="remain-cell-content">0</div>
            </div>
          </div>
          <div class="remain-column">
            <div class="remain-cell">
              <div class="remain-cell-header">2</div>
              <div id="remain-2" class="remain-cell-content">0</div>
            </div>
            <div class="remain-cell">
              <div class="remain-cell-header">5</div>
              <div id="remain-5" class="remain-cell-content">0</div>
            </div>
            <div class="remain-cell">
              <div class="remain-cell-header">8</div>
              <div id="remain-8" class="remain-cell-content">0</div>
            </div>
          </div>
          <div class="remain-column">
            <div class="remain-cell">
              <div class="remain-cell-header">3</div>
              <div id="remain-3" class="remain-cell-content">0</div>
            </div>
            <div class="remain-cell">
              <div class="remain-cell-header">6</div>
              <div id="remain-6" class="remain-cell-content">0</div>
            </div>
            <div class="remain-cell">
              <div class="remain-cell-header">9</div>
              <div id="remain-9" class="remain-cell-content">0</div>
            </div>
          </div>

        </div>
      </li>
    </ul>

    <!--<button class="option-button">
                    <span class="material-icons">pause</span>
                    <span>Pause</span>
                </button>
                <button class="option-button">
                    <span class="material-icons">done_all</span>
                    <span>Check</span>
                </button>
                <button class="option-button">
                    <span class="material-icons">help</span>
                    <span>Hint</span>
                </button>
                <button class="option-button">
                    <span class="material-icons">refresh</span>
                    <span>Restart</span>
                </button>
                <button class="option-button">
                    <span class="material-icons">flag</span>
                    <span>Surrender</span>
                </button>
            -->
  </div>
</div>

<div class="footer vertical-adjust">
  <span class="material-icons">code</span>
  <span>with</span>
  <span class="material-icons">favorite</span>
  <span>by Mohammad Diab from</span>
  <a href="#" onclick="showDialogClick('about-dialog');">#codeTeam6</a>
  <span> . © 2018 all right reserved.</span>
</div>
* {
  box-sizing: border-box;
  margin: 0;
  padding: 0;
  font-family: Roboto, sans-serif;
}

html,
body {
  background-color: rgb(235, 235, 240);
}

table {
  border: 2px solid #000000;
  border-spacing: 0;
  border-collapse: collapse;
  transition: all 0.5s;
}

ul {
  list-style-type: none;
}

td {
  border: 1px solid #000000;
  text-align: center;
  vertical-align: middle;
}

td input {
  color: #000000;
  padding: 0;
  border: 0;
  text-align: center;
  width: 48px;
  height: 48px;
  font-size: 24px;
  background-color: #ffffff;
  outline: none;
  text-transform: uppercase;
  transition: all 0.5s;
}

input:disabled {
  background-color: #bbdefb;
}

tr:nth-child(3n) {
  border-bottom: 4px solid #000000;
}

tr:nth-child(3n + 1) {
  border-top: 4px solid #000000;
}

td:nth-child(3n) {
  border-right: 4px solid #000000;
}

td:nth-child(3n + 1) {
  border-left: 4px solid #000000;
}

.right-cell {
  box-shadow: inset 0px 0px 20px 3px forestgreen;
}

.wrong-cell {
  box-shadow: inset 0px 0px 20px 3px tomato;
}

.worning-cell {
  box-shadow: inset 0px 0px 20px 3px goldenrod;
}

/*Material Design*/

.app-bar {
  background: #49599a;
  width: 100%;
  position: fixed;
  height: 64px;
  color: #fff;
  box-shadow: 0 2px 4px 0 rgba(0, 0, 0, 0.14);
  z-index: 5;
  top: 0;
}

.bar-button {
  position: relative;
  background: transparent;
  border: none;
  outline: none;
  color: #fff;
  vertical-align: middle;
  padding: 0 22px;
  transition: all 0.5s;
}

.bar-button span {
  line-height: 64px;
  display: inline-block;
  vertical-align: middle;
}

.hamburger-button {
  float: left;
  left: 4px;
}

.bar-font {
  font-size: 18px;
  line-height: 64px;
}

.title {
  position: relative;
  float: left;
  left: 18px;
}

.more-button {
  float: right;
  /*right: 18px;*/
}

.hamburger-menu {
  background: rgba(0, 0, 0, 0.4);
  position: fixed;
  left: 0;
  top: 0;
  bottom: 0;
  z-index: 25;
  width: 100vw;
  height: 100vh;
  display: none;
  opacity: 0;
  transition: 0.1s all;
}

.nav-menu {
  border-right: 1px solid rgba(0, 0, 0, 0.4);
  background: #fff;
  color: #212121;
  position: fixed;
  left: -256px;
  top: 0;
  bottom: 0;
  width: 256px;
  z-index: 26;
  font-size: 15px;
  box-shadow: 16px 0 24px 2px rgba(0, 0, 0, 0.14);
  transition: all 0.3s;
}

.nav-menu-blank {
  position: relative;
  left: 256px;
  width: 100%;
  height: 100%;
}

.nav-head {
  height: 172px;
  background: #5e92f3;
  position: relative;
}

.nav-head-img {
  position: relative;
  border: 2px solid rgba(255, 255, 255, 0.4);
  border-radius: 50%;
  width: 96px;
  height: 96px;
  top: 16px;
  left: 16px;
  overflow: hidden;
}

.nav-head-img img {
  width: 100%;
  height: 100%;
}

.nav-head-title {
  color: #fff;
  position: absolute;
  bottom: 10px;
  margin-left: auto;
  margin-right: auto;
  left: 0px;
  right: 0;
  font-size: 22px;
  display: block;
  text-align: center;
}

.nav-items {
  margin-top: 12px;
}

.nav-item {
  font-weight: 700;
  display: block;
  color: #333;
  background: #0000;
  padding: 15px 0 15px 22px;
  letter-spacing: 1.1px;
  outline: none;
  border: none;
  width: 100%;
  text-align: left;
  margin: 0 !important;
}

.bar-footer {
  position: fixed;
  bottom: 12px;
  left: 10px;
}

.bar-footer-link {
  font-size: 12px;
  display: inline-block;
  margin: 0 8px;
  text-decoration: none;
  color: gray;
}

.body {
  width: 95%;
  max-width: 800px;
  margin: 96px auto 16px auto;
  display: flex;
}

.card {
  background: #fff;
  width: fit-content;
  box-shadow: 0 0 4px 0 rgba(0, 0, 0, 0.14);
  float: left;
  padding: 32px 32px 16px 32px;
}

.status {
  margin-left: 32px;
  padding-top: 10px;
  padding-left: 10px;
}

#game-number {
  font-size: 12px;
  color: gray;
}

.game-status {
  /*display: flex;
    flex-direction: column;
    justify-content: center;
    flex-flow: column;*/
  margin: 0 0 0 22px;
  height: 100%;
}

.game-status li {
  margin: 18px 0 0 0;
}

.vertical-adjust {
  margin: 12px 0;
}

.vertical-adjust span,
.footer a {
  line-height: 24px;
  display: inline-block;
  vertical-align: middle;
}

.option-button {
  display: block;
  margin: 16px 8px 16px 30px;
  width: 130px;
  padding: 8px 10px;
  font-size: 16px;
  border: none;
  outline: none;
  box-shadow: 0 6px 10px 1px rgba(0, 0, 0, 0.14);
  border-radius: 2px;
  transition: all 0.5s;
  text-align: left;
}

.button {
  position: relative;
  overflow: hidden;
  cursor: pointer;
}

.option-button:hover {
  background: #1565c0;
}

.option-button:active {
  background: #3d7df4;
  box-shadow: 0 2px 4px 0 rgba(0, 0, 0, 0.24);
}

.option-button span {
  vertical-align: middle;
  line-height: 24px;
}

.ripple {
  position: absolute;
  background: #fff;
  border-radius: 50%;
  width: 5px;
  height: 5px;
  animation: ripple-effect 1.1s 1 cubic-bezier(0.42, 0, 0.58, 1);
  opacity: 0;
}

@keyframes ripple-effect {
  0% {
    transform: scale(1);
    opacity: 0.4;
  }
  100% {
    transform: scale(100);
    opacity: 0;
  }
}

.timer {
  color: #1565c0;
  font-size: 32px;
  padding: 4px;
  box-shadow: 0 0 4px 0 rgba(0, 0, 0, 0.14);
  text-align: center;
}

.remain-table {
  position: relative;
  left: 0;
  right: 0;
  display: inline-block;
  margin: auto;
}

.remain-column {
  float: left;
  max-width: 64px;
}

.remain-cell {
  margin: 10px;
  text-align: center;
  border: solid 1px rgba(0, 0, 0, 0.2);
  box-shadow: 0 0 4px 0 rgba(0, 0, 0, 0.14);
}

.remain-cell div {
  padding: 5px 12px;
}

.remain-cell-header {
  background-color: #1565c0;
  color: white;
  font-weight: bold;
  border-bottom: solid 2px rgba(0, 0, 0, 0.2);
}

.red {
  background: #ff6659;
  color: #9a0007;
}

.gray {
  background: #808080;
  color: #404040;
}

.floating {
  position: fixed;
  bottom: 64px;
  right: 64px;
  z-index: 20;
}

.floating-btn {
  position: fixed;
  bottom: 48px;
  right: 48px;
  border-radius: 50%;
  padding: 12px;
  border: none;
  background-color: #1565c0;
  color: #fff;
  box-shadow: 0 6px 10px 0 rgba(0, 0, 0, 0.14);
  outline: none;
  z-index: 21;
}

.dialog {
  position: absolute;
  left: 0;
  top: 0;
  width: 100%;
  height: 100%;
  background-color: rgba(0, 0, 0, 0.4);
  z-index: 50;
  display: none;
  transition: all 0.2s;
}

.dialog-content {
  top: -200px;
  background: #fff;
  width: 90%;
  max-width: 540px;
  height: fit-content;
  margin: auto;
  vertical-align: middle;
  box-shadow: 0 24px 38px 3px rgba(0, 0, 0, 0.14);
  z-index: 51;
  transition: all 0.5s;
}

.dialog-header {
  font-size: 24px;
  font-weight: bold;
  padding: 16px 32px;
  border-bottom: solid 1px #808080;
}

.dialog-body p {
  margin: 16px 0 4px 28px;
  color: gray;
}

.radio-option {
  padding: 0 36px;
  list-style-type: none;
  position: relative;
}

.radio-option input {
  outline: none;
  margin-right: 12px;
}

.radio-option label {
  display: block;
  height: 24px;
  cursor: pointer;
  padding: 1.25em 0;
}

.dialog-footer {
  border-top: solid 1px #808080;
  margin-top: 24px;
  text-align: right;
  padding-right: 16px;
}

.dialog-btn {
  background: transparent;
  border: none;
  color: #003c8f;
  font-size: 16px;
  margin: 8px 0;
  padding: 8px 16px;
  outline: none;
  min-width: 96px;
  display: inline-block;
}

.footer {
  text-align: center;
  color: white;
  background-color: #49599a;
  margin: 44px 0 0 0;
  padding: 8px;
}

.footer a {
  color: white;
}

.about-dialog-content {
  max-width: 720px;
}

.card-group {
  overflow: hidden;
  width: fit-content;
  margin: 0 auto;
  padding: 16px 0;
  display: flex;
}

.dialog-card {
  padding: 16px;
  margin: 8px;
  max-width: 160px;
}

.about-card-quote {
  color: #606060;
  font-size: 14px;
  margin-top: 16px;
}

.about-card-img {
  margin: 16px auto;
  overflow: hidden;
  border-radius: 50%;
  box-shadow: 0 0 4px 0 rgba(0, 0, 0, 0.14);
  width: fit-content;
}

.about-card-img img {
  width: 96px;
  height: auto;
}

.about-card-title {
  font-size: 16px;
  margin: 8px 0;
}

.about-card-content {
  font-size: 15px;
  margin: 4px 0;
}

.more-option-div {
  position: static;
  display: inline-block;
  margin-right: 16px;
}

.more-option-list {
  display: block;
  position: absolute;
  background-color: #fff;
  overflow: hidden;
  box-shadow: 0px 8px 10px 1px rgba(0, 0, 0, 0.14);
  right: 18px;
  z-index: 25;
  transition: all 0.2s cubic-bezier(0.4, 0, 0.6, 1);
}
// grid variable
var table;

// game number
var gameId = 0;

// puzzle grid
var puzzle = [];

// solution grid
var solution = [];

// remaining number counts
var remaining = [9, 9, 9, 9, 9, 9, 9, 9, 9];

// variable to check if "Sudoku Solver" solve the puzzle
var isSolved = false;
var canSolved = true;

// stopwatch timer variables
var timer = 0;
var pauseTimer = false;
var intervalId;
var gameOn = false;

function newGame(difficulty) {
  // get random position for numbers from '1' to '9' to generate a random puzzle
  var grid = getGridInit();

  // prepare rows, columns and blocks to solove the initioaled grid
  var rows = grid;
  var cols = getColumns(grid);
  var blks = getBlocks(grid);

  //          solve the grid section
  // generate allowed digits for each cell
  var psNum = generatePossibleNumber(rows, cols, blks);

  // solve the grid
  solution = solveGrid(psNum, rows, true);

  // reset the game state timer and remaining number
  timer = 0;
  for (var i in remaining) remaining[i] = 9;

  // empty cells from grid depend on difficulty
  // for now it will be:
  // 59 empty cells for very easy
  // 64 empty cells for easy
  // 69 empty cells for normal
  // 74 empty cells for hard
  // 79 empty cells for expert
  puzzle = makeItPuzzle(solution, difficulty);

  // game is on when the difficulty = [0, 4]
  gameOn = difficulty < 5 && difficulty >= 0;

  // update the UI
  ViewPuzzle(puzzle);
  updateRemainingTable();

  // finally, start the timer
  if (gameOn) startTimer();
}

function getGridInit() {
  var rand = [];
  // for each digits from 1 to 9 find a random row and column
  for (var i = 1; i <= 9; i++) {
    var row = Math.floor(Math.random() * 9);
    var col = Math.floor(Math.random() * 9);
    var accept = true;
    for (var j = 0; j < rand.length; j++) {
      // if number exist or there is a number already located in then ignore and try again
      if ((rand[j][0] == i) | ((rand[j][1] == row) & (rand[j][2] == col))) {
        accept = false;

        // try to get a new position for this number
        i--;
        break;
      }
    }
    if (accept) {
      rand.push([i, row, col]);
    }
  }

  // initialize new empty grid
  var result = [];
  for (var i = 0; i < 9; i++) {
    var row = "000000000";
    result.push(row);
  }

  // put numbers in the grid
  for (var i = 0; i < rand.length; i++) {
    result[rand[i][1]] = replaceCharAt(
      result[rand[i][1]],
      rand[i][2],
      rand[i][0]
    );
  }

  return result;
}

// return columns from a row grid
function getColumns(grid) {
  var result = ["", "", "", "", "", "", "", "", ""];
  for (var i = 0; i < 9; i++) {
    for (var j = 0; j < 9; j++) result[j] += grid[i][j];
    /*try {
            result[j] += grid[i][j];
        } catch (err) {
            alert(grid);
        }*/
  }
  return result;
}

// return blocks from a row grid
function getBlocks(grid) {
  var result = ["", "", "", "", "", "", "", "", ""];
  for (var i = 0; i < 9; i++) {
    for (var j = 0; j < 9; j++)
      result[Math.floor(i / 3) * 3 + Math.floor(j / 3)] += grid[i][j];
  }
  return result;
}

// function to replace char in string
function replaceCharAt(string, index, char) {
  if (index > string.length - 1) return string;
  return string.substr(0, index) + char + string.substr(index + 1);
}

// get allowed numbers that can be placed in each cell
function generatePossibleNumber(rows, columns, blocks) {
  var psb = [];

  // for each cell get numbers that are not viewed in a row, column or block
  // if the cell is not empty then, allowed number is the number already exist in it
  for (var i = 0; i < 9; i++) {
    for (var j = 0; j < 9; j++) {
      psb[i * 9 + j] = "";
      if (rows[i][j] != 0) {
        psb[i * 9 + j] += rows[i][j];
      } else {
        for (var k = "1"; k <= "9"; k++) {
          if (!rows[i].includes(k))
            if (!columns[j].includes(k))
              if (
                !blocks[Math.floor(i / 3) * 3 + Math.floor(j / 3)].includes(k)
              )
                psb[i * 9 + j] += k;
        }
      }
    }
  }
  return psb;
}

function solveGrid(possibleNumber, rows, startFromZero) {
  var solution = [];

  // solve Sudoku with a backtracking algorithm
  // Steps are:
  //  1.  get all allowed numbers that fit in each empty cell
  //  2.  generate all possible rows that fit in the first row depend on the allowed number list
  //` 3.  select one row from possible row list and put it in the first row
  //  4.  go to next row and find all possible number that fit in each cell
  //  5.  generate all possible row fit in this row then go to step 3 until reach the last row or there aren't any possible rows left
  //  6.  if next row hasn't any possible left then go the previous row and try the next possibility from possibility rows' list
  //  7.  if the last row has reached and a row fit in it has found then the grid has solved

  var result = nextStep(0, possibleNumber, rows, solution, startFromZero);
  if (result == 1) return solution;
}

// level is current row number in the grid
function nextStep(level, possibleNumber, rows, solution, startFromZero) {
  // get possible number fit in each cell in this row
  var x = possibleNumber.slice(level * 9, (level + 1) * 9);

  // generate possible numbers sequence that fit in the current row
  var y = generatePossibleRows(x);
  if (y.length == 0) return 0;

  // to allow check is solution is unique
  var start = startFromZero ? 0 : y.length - 1;
  var stop = startFromZero ? y.length - 1 : 0;
  var step = startFromZero ? 1 : -1;
  var condition = startFromZero ? start <= stop : start >= stop;

  // try every numbers sequence in this list and go to next row
  for (var num = start; condition; num += step) {
    var condition = startFromZero ? num + step <= stop : num + step >= stop;
    for (var i = level + 1; i < 9; i++) solution[i] = rows[i];
    solution[level] = y[num];
    if (level < 8) {
      /*if (solution[4] === undefined) {
                var x = 0;
                x++;
            }*/
      var cols = getColumns(solution);
      var blocks = getBlocks(solution);

      var poss = generatePossibleNumber(solution, cols, blocks);
      if (nextStep(level + 1, poss, rows, solution, startFromZero) == 1)
        return 1;
    }
    if (level == 8) return 1;
  }
  return -1;
}

// generate possible numbers sequence that fit in the current row
function generatePossibleRows(possibleNumber) {
  var result = [];

  function step(level, PossibleRow) {
    if (level == 9) {
      result.push(PossibleRow);
      return;
    }

    for (var i in possibleNumber[level]) {
      if (PossibleRow.includes(possibleNumber[level][i])) continue;
      step(level + 1, PossibleRow + possibleNumber[level][i]);
    }
  }

  step(0, "");

  return result;
}

// empty cell from grid depends on the difficulty to make the puzzle
function makeItPuzzle(grid, difficulty) {
  /*
        difficulty:
        // expert   : 0;
        // hard     : 1;
        // Normal   : 2;
        // easy     : 3;
        // very easy: 4;
    */

  // empty_cell_count = 5 * difficulty + 20
  // when difficulty = 13, empty_cell_count = 85 > (81 total cells count)
  // so the puzzle is showen as solved grid
  if (!(difficulty < 5 && difficulty > -1)) difficulty = 13;
  var remainedValues = 81;
  var puzzle = grid.slice(0);

  // function to remove value from a cell and its symmetry then return remained values
  function clearValue(grid, x, y, remainedValues) {
    function getSymmetry(x, y) {
      var symX = 8 - x; //Symmetry
      var symY = 8 - y;
      return [symX, symY];
    }
    var sym = getSymmetry(x, y);
    if (grid[y][x] != 0) {
      grid[y] = replaceCharAt(grid[y], x, "0");
      remainedValues--;
      if (x != sym[0] && y != sym[1]) {
        grid[sym[1]] = replaceCharAt(grid[sym[1]], sym[0], "0");
        remainedValues--;
      }
    }
    return remainedValues;
  }

  // remove value from a cell and its symmetry to reach the expected empty cells amount
  while (remainedValues > difficulty * 5 + 20) {
    var x = Math.floor(Math.random() * 9);
    var y = Math.floor(Math.random() * 9);
    remainedValues = clearValue(puzzle, x, y, remainedValues);
  }
  return puzzle;
}

// view grid in html page
function ViewPuzzle(grid) {
  for (var i = 0; i < grid.length; i++) {
    for (var j = 0; j < grid[i].length; j++) {
      var input = table.rows[i].cells[j].getElementsByTagName("input")[0];
      addClassToCell(table.rows[i].cells[j].getElementsByTagName("input")[0]);
      if (grid[i][j] == "0") {
        input.disabled = false;
        input.value = "";
      } else {
        input.disabled = true;
        input.value = grid[i][j];
        remaining[grid[i][j] - 1]--;
      }
    }
  }
}

// read current grid
function readInput() {
  var result = [];
  for (var i = 0; i < 9; i++) {
    result.push("");
    for (var j = 0; j < 9; j++) {
      var input = table.rows[i].cells[j].getElementsByTagName("input")[0];
      if (input.value == "" || input.value.length > 1 || input.value == "0") {
        input.value = "";
        result[i] += "0";
      } else result[i] += input.value;
    }
  }
  return result;
}

// check value if it is correct or wrong
// return:
//  0 for value can't be changed
//  1 for correct value
//  2 for value that hasn't any conflict with other values
//  3 for value that conflict with value in its row, column or block
//  4 for incorect input
function checkValue(value, row, column, block, defaultValue, currectValue) {
  if (value === "" || value === "0") return 0;
  if (!(value > "0" && value < ":")) return 4;
  if (value === defaultValue) return 0;
  if (
    row.indexOf(value) != row.lastIndexOf(value) ||
    column.indexOf(value) != column.lastIndexOf(value) ||
    block.indexOf(value) != block.lastIndexOf(value)
  ) {
    return 3;
  }
  if (value !== currectValue) return 2;
  return 1;
}

// remove old class from input and add a new class to represent current cell's state
function addClassToCell(input, className) {
  // remove old class from input
  input.classList.remove("right-cell");
  input.classList.remove("worning-cell");
  input.classList.remove("wrong-cell");

  if (className != undefined) input.classList.add(className);
}

// update value of remaining numbers in html page
function updateRemainingTable() {
  for (var i = 1; i < 10; i++) {
    var item = document.getElementById("remain-" + i);
    item.innerText = remaining[i - 1];
    item.classList.remove("red");
    item.classList.remove("gray");
    if (remaining[i - 1] === 0) item.classList.add("gray");
    else if (remaining[i - 1] < 0 || remaining[i - 1] > 9)
      item.classList.add("red");
  }
}

// start stopwatch timer
function startTimer() {
  var timerDiv = document.getElementById("timer");
  clearInterval(intervalId);

  // update stopwatch value every one second
  pauseTimer = false;
  intervalId = setInterval(function () {
    if (!pauseTimer) {
      timer++;
      var min = Math.floor(timer / 60);
      var sec = timer % 60;
      timerDiv.innerText =
        (("" + min).length < 2 ? "0" + min : min) +
        ":" +
        (("" + sec).length < 2 ? "0" + sec : sec);
    }
  }, 1000);
}

// solve sudoku function
// input: changeUI boolean      true to allow function to change UI
// output:
//  0 when everything goes right
//  1 when grid is already solved
//  2 when Invalid input
//  3 when no solution
function solveSudoku(changeUI) {
  // read current state
  puzzle = readInput();

  var columns = getColumns(puzzle);
  var blocks = getBlocks(puzzle);

  // check if there is any conflict
  var errors = 0;
  var correct = 0;

  for (var i = 0; i < puzzle.length; i++) {
    for (var j = 0; j < puzzle[i].length; j++) {
      var result = checkValue(
        puzzle[i][j],
        puzzle[i],
        columns[j],
        blocks[Math.floor(i / 3) * 3 + Math.floor(j / 3)],
        -1,
        -1
      );
      correct = correct + (result === 2 ? 1 : 0);
      errors = errors + (result > 2 ? 1 : 0);
      addClassToCell(
        table.rows[i].cells[j].getElementsByTagName("input")[0],
        result > 2 ? "wrong-cell" : undefined
      );
    }
  }

  // check if invalid input
  if (errors > 0) {
    canSolved = false;
    return 2;
  }

  canSolved = true;
  isSolved = true;

  // check if grid is already solved
  if (correct === 81) {
    return 1;
  }

  //read the current time
  var time = Date.now();

  // solve the grid
  solution = solveGrid(
    generatePossibleNumber(puzzle, columns, blocks),
    puzzle,
    true
  );

  // show result
  // get time
  time = Date.now() - time;

  if (changeUI)
    document.getElementById("timer").innerText =
      Math.floor(time / 1000) + "." + ("000" + (time % 1000)).slice(-3);

  if (solution === undefined) {
    isSolved = false;
    canSolved = false;
    return 3;
  }

  if (changeUI) {
    remaining = [0, 0, 0, 0, 0, 0, 0, 0, 0];
    updateRemainingTable();
    ViewPuzzle(solution);
  }
  return 0;
}

// hide more option menu
function hideMoreOptionMenu() {
  var moreOptionList = document.getElementById("more-option-list");
  if (moreOptionList.style.visibility == "visible") {
    moreOptionList.style.maxWidth = "40px";
    moreOptionList.style.minWidth = "40px";
    moreOptionList.style.maxHeight = "10px";
    moreOptionList.style.opacity = "0";
    setTimeout(function () {
      moreOptionList.style.visibility = "hidden";
    }, 175);
  }
}

// UI Comunication functions

// function that must run when document loaded
window.onload = function () {
  // assigne table to its value
  table = document.getElementById("puzzle-grid");
  // add ripple effect to all buttons in layout
  var rippleButtons = document.getElementsByClassName("button");
  for (var i = 0; i < rippleButtons.length; i++) {
    rippleButtons[i].onmousedown = function (e) {
      // get ripple effect's position depend on mouse and button position
      var x = e.pageX - this.offsetLeft;
      var y = e.pageY - this.offsetTop;

      // add div that represents the ripple
      var rippleItem = document.createElement("div");
      rippleItem.classList.add("ripple");
      rippleItem.setAttribute("style", "left: " + x + "px; top: " + y + "px");

      // if ripple item should have special color... get and apply it
      var rippleColor = this.getAttribute("ripple-color");
      if (rippleColor) rippleItem.style.background = rippleColor;
      this.appendChild(rippleItem);

      // set timer to remove the dif after the effect ends
      setTimeout(function () {
        rippleItem.parentElement.removeChild(rippleItem);
      }, 1500);
    };
  }
  for (var i = 0; i < 9; i++) {
    for (var j = 0; j < 9; j++) {
      var input = table.rows[i].cells[j].getElementsByTagName("input")[0];

      // add function to remove color from cells and update remaining numbers table when it get changed
      input.onchange = function () {
        //remove color from cell
        addClassToCell(this);

        // check if the new value entered is allowed
        function checkInput(input) {
          if (input.value[0] < "1" || input.value[0] > "9") {
            if (input.value != "?" && input.value != "؟") {
              input.value = "";
              alert("only numbers [1-9] and question mark '?' are allowed!!");
              input.focus();
            }
          }
        }
        checkInput(this);

        // compare old value and new value then update remaining numbers table
        if (this.value > 0 && this.value < 10) remaining[this.value - 1]--;
        if (this.oldvalue !== "") {
          if (this.oldvalue > 0 && this.oldvalue < 10)
            remaining[this.oldvalue - 1]++;
        }

        //reset canSolved value when change any cell
        canSolved = true;

        updateRemainingTable();
      };

      //change cell 'old value' when it got focused to track numbers and changes on grid
      input.onfocus = function () {
        this.oldvalue = this.value;
      };
    }
  }
};

// function to hide dialog opened in window
window.onclick = function (event) {
  var d1 = document.getElementById("dialog");
  var d2 = document.getElementById("about-dialog");
  var m1 = document.getElementById("more-option-list");

  if (event.target == d1) {
    hideDialogButtonClick("dialog");
  } else if (event.target == d2) {
    hideDialogButtonClick("about-dialog");
  } else if (m1.style.visibility == "visible") {
    hideMoreOptionMenu();
  }
};

// show hamburger menu
function HamburgerButtonClick() {
  debugger
  var div = document.getElementById("hamburger-menu");
  var menu = document.getElementById("nav-menu");
  div.style.display = "block";
  div.style.visibility = "visible";
  setTimeout(function () {
    div.style.opacity = 1;
    menu.style.left = 0;
  }, 50);
}

// start new game
function startGameButtonClick() {
  var difficulties = document.getElementsByName("difficulty");
  // difficulty:
  //  0 expert
  //  1 hard
  //  2 normal
  //  3 easy
  //  4 very easy
  //  5 solved

  // initial difficulty to 5 (solved)
  var difficulty = 5;

  // get difficulty value
  for (var i = 0; i < difficulties.length; i++) {
    if (difficulties[i].checked) {
      newGame(4 - i);
      difficulty = i;
      break;
    }
  }
  if (difficulty > 4) newGame(5);

  hideDialogButtonClick("dialog");
  gameId++;
  document.getElementById("game-number").innerText = "game #" + gameId;

  // hide solver buttons
  // show other buttons
  document.getElementById("moreoption-sec").style.display = "block";
  document.getElementById("pause-btn").style.display = "block";
  document.getElementById("check-btn").style.display = "block";
  document.getElementById("isunique-btn").style.display = "none";
  document.getElementById("solve-btn").style.display = "none";

  // prerpare view for new game
  document.getElementById("timer-label").innerText = "Time";
  document.getElementById("timer").innerText = "00:00";
  document.getElementById("game-difficulty-label").innerText =
    "Game difficulty";

  document.getElementById("game-difficulty").innerText =
    difficulty < difficulties.length
      ? difficulties[difficulty].value
      : "solved";
}

// pause \ continue button click function
function pauseGameButtonClick() {
  var icon = document.getElementById("pause-icon");
  var label = document.getElementById("pause-text");

  // change icon and label of the button and hide or show the grid
  if (pauseTimer) {
    icon.innerText = "pause";
    label.innerText = "Pause";
    table.style.opacity = 1;
  } else {
    icon.innerText = "play_arrow";
    label.innerText = "Continue";
    table.style.opacity = 0;
  }

  pauseTimer = !pauseTimer;
}

// check grid if correct
function checkButtonClick() {
  // check if game is started
  if (gameOn) {
    // add one minute to the stopwatch as a cost of grid's check
    timer += 60;
    var currentGrid = [];

    // read gritd status
    currentGrid = readInput();

    var columns = getColumns(currentGrid);
    var blocks = getBlocks(currentGrid);

    var errors = 0;
    var currects = 0;

    for (var i = 0; i < currentGrid.length; i++) {
      for (var j = 0; j < currentGrid[i].length; j++) {
        if (currentGrid[i][j] == "0") continue;

        // check value if it is correct or wrong
        var result = checkValue(
          currentGrid[i][j],
          currentGrid[i],
          columns[j],
          blocks[Math.floor(i / 3) * 3 + Math.floor(j / 3)],
          puzzle[i][j],
          solution[i][j]
        );

        // remove old class from input and add a new class to represent current cell's state
        addClassToCell(
          table.rows[i].cells[j].getElementsByTagName("input")[0],
          result === 1
            ? "right-cell"
            : result === 2
            ? "worning-cell"
            : result === 3
            ? "wrong-cell"
            : undefined
        );

        if (result === 1 || result === 0) {
          currects++;
        } else if (result === 3) {
          errors++;
        }
      }
    }

    // if all values are correct and they equal original values then game over and the puzzle has been solved
    // if all values are correct and they aren't equal original values then game over but the puzzle has not been solved yet
    if (currects === 81) {
      gameOn = false;
      pauseTimer = true;
      document.getElementById("game-difficulty").innerText = "Solved";
      clearInterval(intervalId);
      alert("Congrats, You solved it.");
    } else if (errors === 0 && currects === 0) {
      alert(
        "Congrats, You solved it, but this is not the solution that I want."
      );
    }
  }
}

// restart game
function restartButtonClick() {
  if (gameOn) {
    // reset remaining number table
    for (var i in remaining) remaining[i] = 9;

    // review puzzle
    ViewPuzzle(puzzle);

    // update remaining numbers table
    updateRemainingTable();

    // restart the timer
    // -1 is because it take 1 sec to update the timer so it will start from 0
    timer = -1;
  }
}

// surrender
function SurrenderButtonClick() {
  if (gameOn) {
    // reset remaining number table
    for (var i in remaining) remaining[i] = 9;

    // review puzzle
    ViewPuzzle(solution);

    // update remaining numbers table
    updateRemainingTable();

    // stop the game
    gameOn = false;
    pauseTimer = true;
    clearInterval(intervalId);

    // mark game as solved
    document.getElementById("game-difficulty").innerText = "Solved";
  }
}

// hint
function hintButtonClick() {
  if (gameOn) {
    // get list of empty cells and list of wrong cells
    var empty_cells_list = [];
    var wrong_cells_list = [];
    for (var i = 0; i < 9; i++) {
      for (var j = 0; j < 9; j++) {
        var input = table.rows[i].cells[j].getElementsByTagName("input")[0];
        if (input.value == "" || input.value.length > 1 || input.value == "0") {
          empty_cells_list.push([i, j]);
        } else {
          if (input.value !== solution[i][j]) wrong_cells_list.push([i, j]);
        }
      }
    }

    // check if gird is solved if so stop the game
    if (empty_cells_list.length === 0 && wrong_cells_list.length === 0) {
      gameOn = false;
      pauseTimer = true;
      document.getElementById("game-difficulty").innerText = "Solved";
      clearInterval(intervalId);
      alert("Congrats, You solved it.");
    } else {
      // add one minute to the stopwatch as a cost for given hint
      timer += 60;

      // get random cell from empty or wrong list and put the currect value in it
      var input;
      if (
        (Math.random() < 0.5 && empty_cells_list.length > 0) ||
        wrong_cells_list.length === 0
      ) {
        var index = Math.floor(Math.random() * empty_cells_list.length);
        input = table.rows[empty_cells_list[index][0]].cells[
          empty_cells_list[index][1]
        ].getElementsByTagName("input")[0];
        input.oldvalue = input.value;
        input.value =
          solution[empty_cells_list[index][0]][empty_cells_list[index][1]];
        remaining[input.value - 1]--;
      } else {
        var index = Math.floor(Math.random() * wrong_cells_list.length);
        input = table.rows[wrong_cells_list[index][0]].cells[
          wrong_cells_list[index][1]
        ].getElementsByTagName("input")[0];
        input.oldvalue = input.value;
        remaining[input.value - 1]++;
        input.value =
          solution[wrong_cells_list[index][0]][wrong_cells_list[index][1]];
        remaining[input.value - 1]--;
      }

      // update remaining numbers table
      updateRemainingTable();
    }

    // make updated cell blinking
    var count = 0;
    for (var i = 0; i < 6; i++) {
      setTimeout(function () {
        if (count % 2 == 0) input.classList.add("right-cell");
        else input.classList.remove("right-cell");
        count++;
      }, i * 750);
    }
  }
}

function showDialogClick(dialogId) {
  // to hide navigation bar if it opened
  hideHamburgerClick();

  var dialog = document.getElementById(dialogId);
  var dialogBox = document.getElementById(dialogId + "-box");
  dialogBox.focus();
  dialog.style.opacity = 0;
  dialogBox.style.marginTop = "-500px";
  dialog.style.display = "block";
  dialog.style.visibility = "visible";

  // to view and move the dialog to the correct position after it set visible
  setTimeout(function () {
    dialog.style.opacity = 1;
    dialogBox.style.marginTop = "64px";
  }, 200);
}

// show more option menu
function moreOptionButtonClick() {
  var moreOptionList = document.getElementById("more-option-list");

  // timeout to avoid hide menu immediately in window event
  setTimeout(function () {
    if (moreOptionList.style.visibility == "hidden") {
      moreOptionList.style.visibility = "visible";
      setTimeout(function () {
        moreOptionList.style.maxWidth = "160px";
        moreOptionList.style.minWidth = "160px";
        moreOptionList.style.maxHeight = "160px";
        moreOptionList.style.opacity = "1";
      }, 50);
    }
  }, 50);
}

function hideDialogButtonClick(dialogId) {
  var dialog = document.getElementById(dialogId);
  var dialogBox = document.getElementById(dialogId + "-box");
  dialog.style.opacity = 0;
  dialogBox.style.marginTop = "-500px";

  setTimeout(function () {
    dialog.style.visibility = "collapse";
    //dialog.style.display = "none";
  }, 500);
}

// hide hamburger menu when click outside
function hideHamburgerClick() {
  var div = document.getElementById("hamburger-menu");
  var menu = document.getElementById("nav-menu");
  menu.style.left = "-256px";

  setTimeout(function () {
    div.style.opacity = 0;
    //divstyle.display = "none";
    div.style.visibility = "collapse";
  }, 200);
}

// sudoku solver section

function sudokuSolverMenuClick() {
  // hide hamburger menu
  hideHamburgerClick();

  //stop current game if its running
  if (gameOn) {
    gameOn = false;
    clearInterval(intervalId);
  }

  solution = [];
  canSolved = true;
  isSolved = false;

  // generate empty grid
  var grid = [];
  for (var i = 0; i < 9; i++) {
    grid.push("");
    for (var j = 0; j < 9; j++) {
      grid[i] += "0";
    }
  }

  // view empty grid... allow user to edit all cells
  ViewPuzzle(grid);

  // update remaining table
  remaining = [9, 9, 9, 9, 9, 9, 9, 9, 9];
  updateRemainingTable();

  // show solve and check unique buttons
  // hide other buttons
  document.getElementById("moreoption-sec").style.display = "none";
  document.getElementById("pause-btn").style.display = "none";
  document.getElementById("check-btn").style.display = "none";
  document.getElementById("isunique-btn").style.display = "block";
  document.getElementById("solve-btn").style.display = "block";

  // change status card view
  // timer for time takes to solve grid
  // gameid show text "sudoku solver"
  // difficulty show if grid solved is unique
  document.getElementById("timer-label").innerText = "Solve time";
  document.getElementById("timer").innerText = "00:00";
  document.getElementById("game-difficulty-label").innerText = "Is unique";
  document.getElementById("game-difficulty").innerText = "Unknown";
  document.getElementById("game-number").innerText = "#Soduko_Solver";

  //focus first cell
  document
    .getElementById("puzzle-grid")
    .rows[0].cells[0].getElementsByTagName("input")[0]
    .focus();
}

function solveButtonClick() {
  if (gameOn) {
    gameOn = false;
    clearInterval(intervalId);
  }

  var result = solveSudoku(true);
  switch (result) {
    case 0:
      alert("SOLVED");
      break;
    case 1:
      alert("This grid is already solved");
      break;
    case 2:
      alert("This grid can't be solved because of an invalid input");
      break;
    case 3:
      alert("this grid has no solution");
      break;
  }
}

function isUniqueButtonClick() {
  // check if gird is already solved
  // if not try to solve it

  if (!isSolved) {
    if (canSolved) solveSudoku(false);
  }
  if (!isSolved) {
    alert("Can't check this grid because it is unsolvable!");
    return;
  }

  // solve it again but start from the end
  var columns = getColumns(puzzle);
  var blocks = getBlocks(puzzle);
  var solution2 = solveGrid(
    generatePossibleNumber(puzzle, columns, blocks),
    puzzle,
    false
  );

  // if tow solutions are equals then it is unique and vice versa
  var unique = true;
  for (var i = 0; i < solution.length; i++) {
    for (var j = 0; j < solution[i].length; j++) {
      if (solution[i][j] !== solution2[i][j]) {
        unique = false;
        break;
      }
      if (!unique) break;
    }
  }

  //display the result
  document.getElementById("game-difficulty").innerText = unique ? "Yes" : "No";
}

External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

This Pen doesn't use any external JavaScript resources.