Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- <!DOCTYPE html>
- <html lang="ja">
- <head>
- <meta charset="UTF-8">
- <title>MineSweeper</title>
- <style>
- td {
- width: 30px;
- height: 30px;
- text-align: center;
- border: 1px solid #000;
- cursor: pointer;
- }
- td:hover {
- background-color: rgba(64, 64, 64, .1);
- }
- input[disabled=true] {
- background-color: lightgray;
- }
- .not-open {
- background-color: gray;
- }
- .open {
- background-color: white;
- }
- </style>
- </head>
- <body>
- <p>
- <label>X: <input type="number" id="x-size" value="9" min="3" max="99"></label>
- <label>Y: <input type="number" id="y-size" value="9" min="3" max="99"></label>
- <label>Mines: <input id="mine-num" type="number" value="0" disabled></label>
- <button id="start-button">Start</button>
- <button id="reset-button">Reset</button>
- </p>
- <div>
- <span>Time: </span>
- <span id="time-hour">00</span>:<span id="time-minute">00</span>:<span id="time-second">00</span>
- </div>
- <div>
- <button id="change-mode" data-mode="mining">β</button>
- </div>
- <div id="mine-field"></div>
- <script>
- const xSizeDom = document.getElementById('x-size');
- const ySizeDom = document.getElementById('y-size');
- const startButton = document.getElementById('start-button');
- const resetButton = document.getElementById('reset-button');
- const changeModeButton = document.getElementById('change-mode');
- const timeH = document.getElementById('time-hour');
- const timeM = document.getElementById('time-minute');
- const timeS = document.getElementById('time-second');
- const modes = {mining: 'β', flag: 'π©', unknown: 'β'};
- let intervalId, started = false, gameover = false;
- let fieldData = [];
- function init() {
- const x = xSizeDom.value || 9;
- const y = ySizeDom.value || 9;
- renderField(x, y);
- stopTick();
- gameover = false;
- started = false;
- xSizeDom.removeAttribute('disabled');
- ySizeDom.removeAttribute('disabled');
- startButton.removeAttribute('disabled');
- timeH.innerText = timeM.innerText = timeS.innerText = '00';
- changeModeButton.innerText = modes.mining;
- changeModeButton.setAttribute('data-mode', 'mining');
- }
- function start() {
- xSizeDom.setAttribute('disabled', true);
- ySizeDom.setAttribute('disabled', true);
- startButton.setAttribute('disabled', true);
- startTick();
- }
- xSizeDom.onchange = xSizeDom.onkeyup = (e) => {
- init();
- renderField(e.target.value, ySizeDom.value);
- };
- ySizeDom.onchange = ySizeDom.onkeyup = (e) => {
- init();
- renderField(xSizeDom.value, e.target.value);
- };
- startButton.onclick = start;
- resetButton.onclick = init;
- changeModeButton.onclick = (e) => {
- let mode = e.target.getAttribute('data-mode');
- let nextMode;
- switch (mode) {
- case 'mining':
- nextMode = 'flag';
- break;
- case 'flag':
- nextMode = 'unknown';
- break;
- case 'unknown':
- default:
- nextMode = 'mining';
- break;
- }
- e.target.setAttribute('data-mode', nextMode);
- e.target.innerText = modes[nextMode];
- };
- window.onload = () => {
- const x = xSizeDom.value || 9;
- const y = ySizeDom.value || 9;
- renderField(x, y);
- };
- function renderField(x, y) {
- fieldData = [];
- const deleteTarget = document.querySelector('#mine-field table');
- if (deleteTarget) deleteTarget.parentElement.removeChild(deleteTarget);
- const table = document.createElement('table');
- for (let i = 1; i <= x; i++) {
- const tr = document.createElement('tr');
- let fieldRow = [];
- for (let j = 1; j <= y; j++) {
- const td = document.createElement('td');
- td.innerHTML = ' ';
- td.classList.add('not-open');
- td.setAttribute('data-position', `${i},${j}`);
- td.onclick = open;
- tr.appendChild(td);
- fieldRow.push(false);
- }
- fieldData.push(fieldRow);
- table.appendChild(tr);
- }
- const mf = document.getElementById('mine-field');
- mf.appendChild(table);
- document.getElementById('mine-num').value = generateMines(x, y);
- }
- function generateMines(x, y) {
- const mineNum = Math.round((x * y) * 0.3);
- for (let i = 0; i < mineNum; i++) {
- let bombX = Math.floor(Math.random() * x);
- let bombY = Math.floor(Math.random() * y);
- fieldData[bombX][bombY] = true;
- }
- return mineNum;
- }
- function tickTack(h, m, s) {
- h = h || 0;
- m = m || 0;
- s = s || 0;
- if (++s >= 60) {
- s -= 60;
- if (++m >= 60) {
- m -= 60;
- h++;
- timeH.innerText = ('0' + h).slice(-2);
- }
- timeM.innerText = ('0' + m).slice(-2);
- }
- timeS.innerText = ('0' + s).slice(-2);
- }
- function startTick() {
- if (started || gameover) return;
- started = true;
- intervalId = setInterval(function () {
- tickTack(timeH.innerText, timeM.innerText, timeS.innerText);
- }, 1000);
- }
- function stopTick() {
- clearInterval(intervalId);
- }
- function open(e) {
- if (!started) {
- start();
- }
- const target = e.target;
- const mode = changeModeButton.getAttribute('data-mode');
- if (mode === 'mining') {
- let flagged = target.getAttribute('data-flagged');
- if (flagged === 'flag') {
- // ζγη«γ£γ¦γγιγγͺγ
- return;
- }
- target.classList.remove('not-open');
- const position = target.getAttribute('data-position').split(','),
- x = +position[0] - 1, y = +position[1] - 1;
- if (!fieldData[x][y]) {
- target.classList.add('open');
- let num = checkBombNum(x, y);
- if (num === 0) {
- target.innerText = '';
- } else {
- target.innerText = num;
- }
- } else {
- // GameOver
- target.innerText = 'π₯';
- stopTick();
- gameover = true;
- xSizeDom.removeAttribute('disabled');
- ySizeDom.removeAttribute('disabled');
- }
- } else if (mode === 'flag') {
- if (target.classList.contains('open')) {
- // ιγγγ¨γγγ―δ½γγγͺγ
- return;
- }
- let flag = target.getAttribute('data-flagged');
- if (flag === 'flag') {
- target.innerText = '';
- target.setAttribute('data-flagged', '');
- } else {
- target.innerText = modes.flag;
- target.setAttribute('data-flagged', 'flag');
- }
- } else {
- if (target.classList.contains('open')) {
- // ιγγγ¨γγγ―δ½γγγͺγ
- return;
- }
- let flag = target.getAttribute('data-flagged');
- if (flag === 'unknown') {
- target.innerText = '';
- target.setAttribute('data-flagged', '');
- } else {
- target.innerText = modes.unknown;
- target.setAttribute('data-flagged', 'unknown');
- }
- }
- }
- function checkBombNum(x, y) {
- let bombNum = 0;
- for (let i = x - 1; i <= x + 1; i++) {
- if (i < 0 || i >= xSizeDom.value) continue;
- for (let j = y - 1; j <= y + 1; j++) {
- if (j < 0 || j >= xSizeDom.value) continue;
- if (i === x && j === y) continue;
- if (fieldData[i][j]) bombNum++;
- }
- }
- return bombNum;
- }
- </script>
- </body>
- </html>
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement