使用JS实现2048小游戏

JS实现2048小游戏源码

效果图:

代码如下,复制即可使用:

(适用浏览器:360、FireFox、Chrome、Opera、傲游、搜狗、世界之窗. 不支持Safari、IE8及以下浏览器。)

<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0,maximum-scale=1.0,minimum-scale=1.0,user-scalable=0">
<title>使用JS实现2048小游戏</title>
<!-- 此处需要自己修改为自己的css路径  -->
<link rel="stylesheet" href="css/reset.min.css">
<link rel="stylesheet" href="css/style.css">

</head>
<body>

<header>
    <div class="container">
        <h1><span>2</span><span>0</span><span>4</span><span>8</span></h1>
        <p class="inspired">by the原2048的灵感。</p>
    </div>
</header>

<div class="container">
    <div class="directions">
        <p><strong>如何玩:</strong> 使用你的箭头键移动瓷砖。当两个瓦片相互滑动时,它们合并成一个!</p>
    </div>
    <div class="scores">
        <div class="score-container best-score">
            最佳:
            <div class="score">
                <div id="bestScore">0</div>
            </div>
        </div>
        <div class="score-container">
            分数:
            <div class="score">
                <div id="score">0</div>
                <div class="add" id="add"></div>
            </div>
        </div>
    </div>
    <div class="game">
        <div id="tile-container" class="tile-container"></div>
        <div class="end" id="end">游戏结束<div class="monkey"></div><button class="btn not-recommended__item js-restart-btn" id="try-again">再试一次</button></div>
    </div>

    <div class="not-recommended">
        <button class="btn not-recommended__item js-restart-btn" id="restart">重新启动游戏</button>
    </div>

</div>
<!-- 此处需要自己修改JS路径 -->
<script src="js/index.js"></script>

<div style="text-align:center;margin:10px 0; font:normal 14px/24px ‘MicroSoft YaHei‘;">
<p>适用浏览器:360、FireFox、Chrome、Opera、傲游、搜狗、世界之窗. 不支持Safari、IE8及以下浏览器。</p>
</div>
</body>
</html>

reset.min.css

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;border:0;font-size:100%;font:inherit;vertical-align:baseline}article,aside,details,figcaption,figure,footer,header,hgroup,menu,nav,section{display:block}body{line-height:1}ol,ul{list-style:none}blockquote,q{quotes:none}blockquote:before,blockquote:after,q:before,q:after{content:‘‘;content:none}table{border-collapse:collapse;border-spacing:0}

style.css

@charset "UTF-8";
* {
  box-sizing: border-box;
}

a {
  color: #1B9AAA;
  text-decoration: none;
  border-bottom: 1px solid currentColor;
}
a:hover {
  color: #14727e;
}
a:focus, a:active {
  color: #0d4a52;
}

body,
html {
  position: relative;
  width: 100%;
  height: 100%;
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-orient: vertical;
  -webkit-box-direction: normal;
      -ms-flex-direction: column;
          flex-direction: column;
  font-family: "Arvo", Helvetica, sans-serif;
  font-family: 12px;
  color: #555;
  background: #F8FFE5;
}

strong {
  font-weight: bold;
}

p {
  line-height: 1.6;
}

.inspired {
  margin-top: 1em;
  font-size: 0.9rem;
  color: #9a9a95;
}

header {
  color: #F8FFE5;
  text-align: center;
}
header span {
  display: inline-block;
  box-sizing: border-box;
  width: 4rem;
  height: 4rem;
  line-height: 4rem;
  margin: 0 0.4rem;
  background: #FFC43D;
}
header span:nth-of-type(2) {
  background: #EF476F;
}
header span:nth-of-type(3) {
  background: #1B9AAA;
}
header span:nth-of-type(4) {
  background: #06D6A0;
}

h1 {
  font-size: 2.2rem;
}

.directions {
  padding: 2rem;
  border-top: 1px solid #9a9a95;
  border-bottom: 1px solid #9a9a95;
}

.container {
  margin: 0 auto;
  padding-bottom: 3.5rem;
  -webkit-box-flex: 1;
      -ms-flex: 1;
          flex: 1;
  width: 100%;
  max-width: 550px;
  text-align: center;
}
header .container {
  padding: 0;
  padding: 2rem 4rem;
  max-width: 900px;
}

.scores {
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-pack: center;
      -ms-flex-pack: center;
          justify-content: center;
}

.score-container {
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-pack: center;
      -ms-flex-pack: center;
          justify-content: center;
  -webkit-box-align: center;
      -ms-flex-align: center;
          align-items: center;
  margin: 1.8rem;
  font-size: 1.2rem;
  line-height: 1;
  color: #555;
}
.score-container.best-score {
  color: #9a9a95;
}

.score {
  margin-left: 1rem;
  position: relative;
  font-weight: bold;
  font-size: 1.5rem;
  vertical-align: middle;
  text-align: right;
}

.game {
  position: relative;
  margin: 0 auto;
  background: #9a9a95;
  padding: 7px;
  display: inline-block;
  border-radius: 3px;
  box-sizing: border-box;
}

.tile-container {
  border-radius: 6px;
  position: relative;
  width: 400px;
  height: 400px;
}

.tile, .background {
  display: block;
  color: #F8FFE5;
  position: absolute;
  width: 100px;
  height: 100px;
  box-sizing: border-box;
  text-align: center;
}

.background {
  z-index: 1;
  text-align: center;
  border: 7px solid #9a9a95;
  background-color: #F8FFE5;
}

.tile {
  opacity: 0;
  z-index: 2;
  background: #FFC43D;
  color: #F8FFE5;
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-align: center;
      -ms-flex-align: center;
          align-items: center;
  -webkit-box-pack: center;
      -ms-flex-pack: center;
          justify-content: center;
  font-size: 1.8rem;
  align-items: center;
  -webkit-transition: 110ms ease-in-out;
  transition: 110ms ease-in-out;
  border-radius: 3px;
  border: 7px solid #9a9a95;
  box-sizing: border-box;
}
.tile--4 {
  background: #EF476F;
  color: #F8FFE5;
}
.tile--8 {
  background: #1B9AAA;
  color: #F8FFE5;
}
.tile--16 {
  background: #06D6A0;
  color: #F8FFE5;
}
.tile--32 {
  background: #f37694;
  color: #F8FFE5;
}
.tile--64 {
  background: #22c2d6;
  color: #F8FFE5;
}
.tile--128 {
  background: #17f8be;
  color: #F8FFE5;
}
.tile--256 {
  background: #ffd470;
  color: #F8FFE5;
}
.tile--512 {
  background: #eb184a;
  color: #F8FFE5;
}
.tile--1024 {
  background: #14727e;
  color: #F8FFE5;
}
.tile--2048 {
  background: #05a47b;
  color: #F8FFE5;
}
.tile--pop {
  -webkit-animation: pop 0.3s ease-in-out;
          animation: pop 0.3s ease-in-out;
  -webkit-animation-fill-mode: forwards;
          animation-fill-mode: forwards;
}
.tile--shrink {
  -webkit-animation: shrink 0.5s ease-in-out;
          animation: shrink 0.5s ease-in-out;
  -webkit-animation-fill-mode: forwards;
          animation-fill-mode: forwards;
}

.add {
  position: absolute;
  opacity: 0;
  left: 120%;
  top: 0;
  font-size: 1rem;
  color: #1B9AAA;
}
.add.active {
  -webkit-animation: add 0.8s ease-in-out;
          animation: add 0.8s ease-in-out;
}

@-webkit-keyframes add {
  0% {
    opacity: 1;
    top: 0;
  }
  100% {
    opacity: 0;
    top: -100%;
  }
}

@keyframes add {
  0% {
    opacity: 1;
    top: 0;
  }
  100% {
    opacity: 0;
    top: -100%;
  }
}
@-webkit-keyframes pop {
  0% {
    -webkit-transform: scale(0.5);
            transform: scale(0.5);
    opacity: 0;
  }
  90% {
    -webkit-transform: scale(1.1);
            transform: scale(1.1);
    opacity: 1;
  }
  100% {
    -webkit-transform: scale(1);
            transform: scale(1);
    opacity: 1;
  }
}
@keyframes pop {
  0% {
    -webkit-transform: scale(0.5);
            transform: scale(0.5);
    opacity: 0;
  }
  90% {
    -webkit-transform: scale(1.1);
            transform: scale(1.1);
    opacity: 1;
  }
  100% {
    -webkit-transform: scale(1);
            transform: scale(1);
    opacity: 1;
  }
}
@-webkit-keyframes shrink {
  0% {
    -webkit-transform: scale(1);
            transform: scale(1);
    opacity: 1;
  }
  100% {
    -webkit-transform: scale(0.9);
            transform: scale(0.9);
    opacity: 0.9;
  }
}
@keyframes shrink {
  0% {
    -webkit-transform: scale(1);
            transform: scale(1);
    opacity: 1;
  }
  100% {
    -webkit-transform: scale(0.9);
            transform: scale(0.9);
    opacity: 0.9;
  }
}
.end {
  opacity: 0;
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  z-index: -1;
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-orient: vertical;
  -webkit-box-direction: normal;
      -ms-flex-direction: column;
          flex-direction: column;
  -webkit-box-pack: center;
      -ms-flex-pack: center;
          justify-content: center;
  -webkit-box-align: center;
      -ms-flex-align: center;
          align-items: center;
  background: rgba(85, 85, 85, 0.9);
  color: white;
  font-size: 2rem;
  -webkit-transition: opacity 0.3s ease-in-out;
  transition: opacity 0.3s ease-in-out;
}
.end btn {
  margin-top: 1rem;
}
.end.active {
  opacity: 1;
  z-index: 1000;
}

.monkey {
  font-size: 3rem;
  margin: 1rem 0;
}

.btn {
  font-family: inherit;
  font-size: 1rem;
  border: none;
  background: #1B9AAA;
  letter-spacing: 1px;
  color: white;
  font-weight: 300;
  padding: 0.9em 1.5em;
  border-radius: 3px;
  border: 1px solid transparent;
  cursor: pointer;
}
.btn:hover {
  background-color: #14727e;
}
.btn:active {
  background-color: #0d4a52;
}
.btn:focus {
  box-shadow: 0 0 10px #0d4a52 inset;
  outline: none;
}

.not-recommended {
  display: -webkit-box;
  display: -ms-flexbox;
  display: flex;
  -webkit-box-pack: center;
      -ms-flex-pack: center;
          justify-content: center;
  -webkit-box-align: center;
      -ms-flex-align: center;
          align-items: center;
  margin-top: 3rem;
}
.not-recommended * + * {
  margin-left: 10px;
}
.not-recommended__item + .not-recommended__annotation:before {
  font-size: 30px;
  content: "??";
}
.not-recommended__item:hover + .not-recommended__annotation:before {
  content: "??";
}
.not-recommended__item:focus + .not-recommended__annotation:before {
  content: "??";
}
.not-recommended__item:active + .not-recommended__annotation:before {
  content: "??";
}

index.js

‘use strict‘;

var _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; };

var game = null;
var bestScore = 0;
var scoreDiv = document.getElementById(‘score‘);
var bestScoreDiv = document.getElementById(‘bestScore‘);
var addDiv = document.getElementById(‘add‘);
var endDiv = document.getElementById(‘end‘);
var size = 4;
var nextId = 1;
var score = 0;

function initGame() {
  game = Array(size * size).fill(null); // 4 x 4 grid, represented as an array
  initBestScore();
}

function initBestScore() {
  bestScore = localStorage.getItem(‘bestScore‘) || 0;
  bestScoreDiv.innerHTML = bestScore;
}

function updateDOM(before, after) {
  var newElements = getNewElementsDOM(before, after);
  var existingElements = getExistingElementsDOM(before, after);
  var mergedTiles = getMergedTiles(after);
  removeElements(mergedTiles);
  drawGame(newElements, true);
  drawGame(existingElements);
}

function removeElements(mergedTiles) {
  for (var _iterator = mergedTiles, _isArray = Array.isArray(_iterator), _i = 0, _iterator = _isArray ? _iterator : _iterator[Symbol.iterator]();;) {
    var _ref;

    if (_isArray) {
      if (_i >= _iterator.length) break;
      _ref = _iterator[_i++];
    } else {
      _i = _iterator.next();
      if (_i.done) break;
      _ref = _i.value;
    }

    var tile = _ref;

    var _loop = function _loop() {
      if (_isArray2) {
        if (_i2 >= _iterator2.length) return ‘break‘;
        _ref2 = _iterator2[_i2++];
      } else {
        _i2 = _iterator2.next();
        if (_i2.done) return ‘break‘;
        _ref2 = _i2.value;
      }

      var id = _ref2;

      var currentElm = document.getElementById(id);
      positionTile(tile, currentElm);
      currentElm.classList.add(‘tile--shrink‘);
      setTimeout(function () {
        currentElm.remove();
      }, 100);
    };

    for (var _iterator2 = tile.mergedIds, _isArray2 = Array.isArray(_iterator2), _i2 = 0, _iterator2 = _isArray2 ? _iterator2 : _iterator2[Symbol.iterator]();;) {
      var _ref2;

      var _ret = _loop();

      if (_ret === ‘break‘) break;
    }
  }
}

function getMergedTiles(after) {
  return after.filter(function (tile) {
    return tile && tile.mergedIds;
  });
}

function getNewElementsDOM(before, after) {
  var beforeIds = before.filter(function (tile) {
    return tile;
  }).map(function (tile) {
    return tile.id;
  });
  var newElements = after.filter(function (tile) {
    return tile && beforeIds.indexOf(tile.id) === -1;
  });
  return newElements;
}

function getExistingElementsDOM(before, after) {
  var beforeIds = before.filter(function (tile) {
    return tile;
  }).map(function (tile) {
    return tile.id;
  });
  var existingElements = after.filter(function (tile) {
    return tile && beforeIds.indexOf(tile.id) !== -1;
  });
  return existingElements;
}

function drawBackground() {
  var tileContainer = document.getElementById(‘tile-container‘);
  tileContainer.innerHTML = ‘‘;
  for (var i = 0; i < game.length; i++) {
    var tile = game[i];
    var tileDiv = document.createElement(‘div‘);
    var x = i % size;
    var y = Math.floor(i / size);
    tileDiv.style.top = y * 100 + ‘px‘;
    tileDiv.style.left = x * 100 + ‘px‘;

    tileDiv.classList.add("background");
    tileContainer.appendChild(tileDiv);
  }
}

function positionTile(tile, elm) {
  var x = tile.index % size;
  var y = Math.floor(tile.index / size);
  elm.style.top = y * 100 + ‘px‘;
  elm.style.left = x * 100 + ‘px‘;
}

function drawGame(tiles, isNew) {
  var tileContainer = document.getElementById(‘tile-container‘);
  for (var i = 0; i < tiles.length; i++) {
    var tile = tiles[i];
    if (tile) {
      if (isNew) {
        (function () {
          var tileDiv = document.createElement(‘div‘);
          positionTile(tile, tileDiv);
          tileDiv.classList.add(‘tile‘, ‘tile--‘ + tile.value);
          tileDiv.id = tile.id;
          setTimeout(function () {
            tileDiv.classList.add("tile--pop");
          }, tile.mergedIds ? 1 : 150);
          tileDiv.innerHTML = ‘<p>‘ + tile.value + ‘</p>‘;
          tileContainer.appendChild(tileDiv);
        })();
      } else {
        var currentElement = document.getElementById(tile.id);
        positionTile(tile, currentElement);
      }
    }
  }
}

function gameOver() {
  if (game.filter(function (number) {
    return number === null;
  }).length === 0) {
    var sameNeighbors = game.find(function (tile, i) {
      var isRightSame = game[i + 1] && (i + 1) % 4 !== 0 ? tile.value === game[i + 1].value : false;
      var isDownSame = game[i + 4] ? tile.value === game[i + 4].value : false;
      if (isRightSame || isDownSame) {
        return true;
      }
      return false;
    });
    return !sameNeighbors;
  }
}

function generateNewNumber() {
  // 0.9 probability of 2, 0.1 probability of 4
  var p = Math.random() * 100;
  return p <= 90 ? 2 : 4;
}

function addRandomNumber() {
  // Adds either a 2 or a 4 to an empty position in the game array
  var emptyCells = game.map(function (_, index) {
    return index;
  }).filter(function (index) {
    return game[index] === null;
  });
  if (emptyCells.length === 0) {
    return;
  }
  var newPos = emptyCells[Math.floor(Math.random() * emptyCells.length)];
  var newObj = {
    id: nextId++,
    index: newPos,
    value: generateNewNumber()
  };
  game.splice(newPos, 1, newObj);
}

function getIndexForPoint(x, y) {
  return y * size + x;
}

function reflectGrid(grid) {
  var reflectedGame = Array(size * size).fill(0);
  for (var row = 0; row < size; row++) {
    for (var col = 0; col < size; col++) {
      var index1 = getIndexForPoint(col, row);
      var index2 = getIndexForPoint(size - col - 1, row);
      reflectedGame[index1] = grid[index2];
    }
  }
  return reflectedGame;
}

function rotateLeft90Deg(grid) {
  var rotatedGame = Array(size * size).fill(0);
  for (var row = 0; row < size; row++) {
    for (var col = 0; col < size; col++) {
      var index1 = getIndexForPoint(col, row);
      var index2 = getIndexForPoint(size - 1 - row, col);
      rotatedGame[index1] = grid[index2];
    }
  }
  return rotatedGame;
}

function rotateRight90Deg(grid) {
  var rotatedGame = Array(size * size).fill(0);
  for (var row = 0; row < size; row++) {
    for (var col = 0; col < size; col++) {
      var index1 = getIndexForPoint(col, row);
      var index2 = getIndexForPoint(row, size - 1 - col);
      rotatedGame[index1] = grid[index2];
    }
  }
  return rotatedGame;
}

/*
For any cell whose neighbor to the right is empty, move that cell
to the right. For any cell whose neighbor to the right is equal
to the same value, combine the values together (e.g. 2+2 = 4)
*/
function shiftGameRight(gameGrid) {
  // reflect game grid
  var reflectedGame = reflectGrid(gameGrid);
  // shift left
  reflectedGame = shiftGameLeft(reflectedGame);
  // reflect back
  return reflectGrid(reflectedGame);
}

function shiftGameLeft(gameGrid) {
  var newGameState = [];
  var totalAdd = 0;
  // for rows
  for (var i = 0; i < size; i++) {
    // for columns
    var firstPos = 4 * i;
    var lastPos = size + 4 * i;
    var currentRow = gameGrid.slice(firstPos, lastPos);
    var filteredRow = currentRow.filter(function (row) {
      return row;
    });
    for (var _iterator3 = filteredRow, _isArray3 = Array.isArray(_iterator3), _i3 = 0, _iterator3 = _isArray3 ? _iterator3 : _iterator3[Symbol.iterator]();;) {
      var _ref3;

      if (_isArray3) {
        if (_i3 >= _iterator3.length) break;
        _ref3 = _iterator3[_i3++];
      } else {
        _i3 = _iterator3.next();
        if (_i3.done) break;
        _ref3 = _i3.value;
      }

      var row = _ref3;

      delete row.mergedIds;
    }

    for (var j = 0; j < filteredRow.length - 1; j++) {
      if (filteredRow[j].value === filteredRow[j + 1].value) {
        var sum = filteredRow[j].value * 2;
        filteredRow[j] = {
          id: nextId++,
          mergedIds: [filteredRow[j].id, filteredRow[j + 1].id],
          value: sum
        };
        filteredRow.splice(j + 1, 1);
        score += sum;
        totalAdd += sum;
      }
    }
    while (filteredRow.length < size) {
      filteredRow.push(null);
    };
    newGameState = [].concat(newGameState, filteredRow);
  }

  if (totalAdd > 0) {
    scoreDiv.innerHTML = score;
    addDiv.innerHTML = ‘+‘ + totalAdd;
    addDiv.classList.add(‘active‘);
    setTimeout(function () {
      addDiv.classList.remove("active");
    }, 800);
    if (score > bestScore) {
      localStorage.setItem(‘bestScore‘, score);
      initBestScore();
    }
  }
  return newGameState;
}

function shiftGameUp(gameGrid) {
  var rotatedGame = rotateLeft90Deg(gameGrid);
  rotatedGame = shiftGameLeft(rotatedGame);
  return rotateRight90Deg(rotatedGame);
}

function shiftGameDown(gameGrid) {
  var rotatedGame = rotateRight90Deg(gameGrid);
  rotatedGame = shiftGameLeft(rotatedGame);
  return rotateLeft90Deg(rotatedGame);
}

var buttons = document.querySelectorAll(".js-restart-btn");
var length = buttons.length;
for (var i = 0; i < length; i++) {
  if (document.addEventListener) {
    buttons[i].addEventListener("click", function () {
      newGameStart();
    });
  } else {
    buttons[i].attachEvent("onclick", function () {
      newGameStart();
    });
  };
};

document.addEventListener("keydown", handleKeypress);
document.addEventListener(‘touchstart‘, handleTouchStart, false);
document.addEventListener(‘touchmove‘, handleTouchMove, false);

var xDown = null;
var yDown = null;

function handleTouchStart(evt) {
  xDown = evt.touches[0].clientX;
  yDown = evt.touches[0].clientY;
};

function handleTouchMove(evt) {
  var prevGame = [].concat(game);
  if (!xDown || !yDown) {
    return;
  }
  var xUp = evt.touches[0].clientX;
  var yUp = evt.touches[0].clientY;

  var xDiff = xDown - xUp;
  var yDiff = yDown - yUp;

  if (Math.abs(xDiff) > Math.abs(yDiff)) {
    if (xDiff > 0) {
      game = shiftGameLeft(game);
    } else {
      game = shiftGameRight(game);
    }
  } else {
    if (yDiff > 0) {
      game = shiftGameUp(game);
    } else {
      game = shiftGameDown(game);
    }
  }
  game = game.map(function (tile, index) {
    if (tile) {
      return _extends({}, tile, {
        index: index
      });
    } else {
      return null;
    }
  });
  addRandomNumber();
  updateDOM(prevGame, game);
  if (gameOver()) {
    setTimeout(function () {
      endDiv.classList.add(‘active‘);
    }, 800);
    return;
  }
  xDown = null;
  yDown = null;
};

function handleKeypress(evt) {
  var modifiers = event.altKey || event.ctrlKey || event.metaKey || event.shiftKey;
  var whichKey = event.which;

  var prevGame = [].concat(game);

  if (!modifiers) {
    event.preventDefault();
    switch (whichKey) {
      case 37:
        game = shiftGameLeft(game);
        break;
      case 38:
        game = shiftGameUp(game);
        break;
      case 39:
        game = shiftGameRight(game);
        break;
      case 40:
        game = shiftGameDown(game);
        break;
    }
    game = game.map(function (tile, index) {
      if (tile) {
        return _extends({}, tile, {
          index: index
        });
      } else {
        return null;
      }
    });
    addRandomNumber();
    updateDOM(prevGame, game);
    if (gameOver()) {
      setTimeout(function () {
        endDiv.classList.add(‘active‘);
      }, 800);
      return;
    }
  }
}

function newGameStart() {
  document.getElementById(‘tile-container‘).innerHTML = ‘‘;
  endDiv.classList.remove(‘active‘);
  score = 0;
  scoreDiv.innerHTML = score;
  initGame();
  drawBackground();
  var previousGame = [].concat(game);
  addRandomNumber();
  addRandomNumber();
  updateDOM(previousGame, game);
}

newGameStart();

如果有更好的方法或更多的功能,可以和我们大家一起分享哦,如有错误,欢迎联系我改正,非常感谢!!!

原文地址:https://www.cnblogs.com/yidaixiaohui/p/8447637.html

时间: 2024-10-27 01:39:20

使用JS实现2048小游戏的相关文章

js实现2048小游戏二维数组更新算法

2048小游戏是当下比较流行的益智游戏了,而它最关键的模块莫过于当手指滑过或鼠标按下后如何确定更新的值. 首先该游戏可以看作一个4*4的二维数组的更新游戏,玩家通过控制数组内元素的合并来不断产生更大的数字,当方向确定时,每一行或每一列的计算方式实际上是一样的,例如,当我确定方向为向左时,每一行的计算方式都是一样的,这样,我们就可以将二维数组的计算简化为一维数组的计算了,然后通过循环计算其他行即可. 而一维数组中主要就是寻找相邻的两个非空值进行合并,相关函数可表示如下: // 一维数组合并相邻非空

js实现2048小游戏

这是学完javascript基础,编写的入门级web小游戏 游戏规则:在玩法规则也非常的简单,一开始方格内会出现2或者4等这两个小数字,玩家只需要上下左右其中一个方向来移动出现的数字,所有的数字就会想滑动的方向靠拢,而滑出的空白方块就会随机出现一个数字,相同的数字相撞时会叠加靠拢,然后一直这样,不断的叠加最终拼凑出2048这个数字就算成功.但是我们的程序没有终点. 一.HTML部分 1 <body> 2 <!-- 分数行 --> 3 <p id="scorePane

用原生js写2048小游戏

WEB前端交流群  172994155  回复 ww 验证  <!DOCTYPE html> <html> <head> <title> 2048-game </title> <meta charset="utf-8" /> <style media="screen"> #game { display: none; position: absolute; left: 0px; top

2048小游戏-JS实现(BUG调试中)

刚刚学习JS的菜鸟,游戏没有实现滑动效果.希望有前辈能指点一下······ 定义的主要方法: 1.fuzhi()生成一对随机数,然后根据这对随机数取得一个随机单元格,先判断其是否为空,不为空,对其进行赋值为2的操作:为空,则再次调用fuzhi(). 2.secai()遍历表格,根据单元格的数值改变单元格的背景颜色. 3.score()遍历单元格,计算实时总得分. 4.keyDown()主要方法,根据用户按上下左右键来进行不同的数值相加.消除动作.这一段代码写得很冗余····· 1 <!DOCTY

js、jQuery实现2048小游戏

一.游戏简介:  2048是一款休闲益智类的数字叠加小游戏 二. 游戏玩法: 在4*4的16宫格中,您可以选择上.下.左.右四个方向进行操作,数字会按方向移动,相邻的两个数字相同就会合并,组成更大的数字,每次移动或合并后会增加一个数字. 当16宫格中没有空格子,且四个方向都无法操作时,游戏结束. 三. 游戏目的: 目的是合并出2048这个数字,获得更高的分数. 四. 游戏截图:  五.先来玩一下: 开始游戏 查看源码 六.游戏实现原理: 使用js.jQuery实现了PC版及手机版,实现原理是一样

【2048小游戏】——CSS/原生js爬坑之纯CSS模态对话框&amp;游戏结束

引言:2048小游戏的结束界面,使用纯CSS制作模态对话框,一般做模态对话框都会使用BootStrap自带的模态对话框组件方便使用,但在制作要运行在移动端的小项目时,就不能使用BootStrap,因为文件太大,下载耗时,耗费流量. 一.模态对话框的组成 2个Div,一个铺满整屛,一个显示内容 坑:如何让Div铺满整屛?解决:2个办法 宽  高 100%    →    position:absolute:  →   top=0;left=0; 四个方向  margin-top/left/righ

【2048小游戏】——原生js爬坑之遍历算法显示二维数组内容

引言:做2048小游戏会将横纵方向的数字内容,存储在一个二维数组中,要将这个二维数组中的内容显示在页面上,就一定要用遍历算法来实现了. 一.二维数组存储    首先考虑用二维数组存储所有行数,列数  →  var  RN=4,CN=4; 然后再定义一个变量data 来保存这个二维数组  →  var  data; 游戏的所有主要执行程序都保存在start()函数下 → 启动游戏 保存存有行数,列数的二维数组到data中    关键代码 ↓ function start(){ data=[]; /

canvas随笔之2048小游戏

HTML: <!DOCTYPE HTML> <html> <head> <title>2048小游戏</title> <meta charset="utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0, minimum-scale=0.5, maximum-scale=2.0, u

JQuery实现2048小游戏

最近用Jqery写了一个2048小游戏,由于是第一次写小游戏,所以就选了一个基础的没什么难度游戏.具体实现如下: 首先在开发时将整个游戏分成两层(自认为),底层是游戏的数据结构以及对数据的操作,上层是显示出来的用户界面.底层选择使用一个4x4的二维数组,整个游戏的数据操作都围绕着这个二维数组进行. [一]游戏基础界面 1 <div id="game"> 2 <div id="header"> 3 <h1>1024</h1&g