<html>
  <head>
    <title>Tetris</title>
    <style>
      body {
        background-color: #222;
        color: #eee;
        font-family: sans-serif;
        text-align: center;
      }
      #canvas {
        border: 5px solid #444;
      }
    </style>
  </head>
  <body>
    <h1>Tetris</h1>
    <canvas id="canvas" width="200" height="400"></canvas>
    <script>
      let canvas = document.getElementById('canvas');
      let ctx = canvas.getContext('2d');
      let score = 0;
      let level = 1;
      let lines = 0;
      let board = [];
      for (let i = 0; i < 20; i++) {
        board[i] = new Array(10).fill(0);
      }
      let current;
      let currentX = 4;
      let currentY = 0;
      let pieces = [
        [1, 1, 1, 1],
        [2, 2, 2],
        [3, 3, 3],
        [4, 4],
        [5, 5, 5],
        [6, 6, 6],
        [7, 7, 7]
      ];
      let colors = ['#2C3E50', '#E74C3C', '#2980B9', '#8E44AD', '#F1C40F', '#27AE60', '#16A085'];
      function draw(){
        ctx.fillStyle = '#222';
        ctx.fillRect(0, 0, canvas.width, canvas.height);
        drawBoard();
        drawPiece();
        drawScore();
      }
      function drawBoard(){
        for (let r = 0; r < 20; r++){
          for (let c = 0; c < 10; c++){
            if (board[r][c] !== 0) {
              ctx.fillStyle = colors[board[r][c] - 1];
              ctx.fillRect(c * 20, r * 20, 20, 20);
            }
          }
        }
      }
      function drawPiece(){
        for (let r = 0; r < current.length; r++){
          for (let c = 0; c < current[r].length; c++){
            if (current[r][c] !== 0) {
              ctx.fillStyle = colors[current[r][c] - 1];
              ctx.fillRect((currentX + c) * 20, (currentY + r) * 20, 20, 20);
            }
          }
        }
      }
      function drawScore(){
        ctx.fillStyle = '#eee';
        ctx.font = '20px sans-serif';
        ctx.fillText(`Score: ${score}`, 110, 20);
        ctx.fillText(`Level: ${level}`, 110, 40);
        ctx.fillText(`Lines: ${lines}`, 110, 60);
      }
      function newPiece(){
        let random = Math.floor(Math.random() * pieces.length);
        current = pieces[random];
        currentX = 4;
        currentY = 0;
      }
      function tick(){
        if (valid(0, 1)) {
          currentY++;
        } else {
          freeze();
          clearLines();
          newPiece();
        }
      }
      function valid(offsetX, offsetY, newCurrent){
        offsetX = offsetX || 0;
        offsetY = offsetY || 0;
        offsetX = currentX + offsetX;
        offsetY = currentY + offsetY;
        newCurrent = newCurrent || current;
        for (let r = 0; r < newCurrent.length; r++){
          for (let c = 0; c < newCurrent[r].length; c++){
            if (newCurrent[r][c] !== 0 &&
                (board[r + offsetY] === undefined ||
                 board[r + offsetY][c + offsetX] === undefined ||
                 board[r + offsetY][c + offsetX] !== 0)) {
                  return false;
            }
          }
        }
        return true;
      }
      function freeze(){
        for (let r = 0; r < current.length; r++){
          for (let c = 0; c < current[r].length; c++){
            if (current[r][c] !== 0) {
              board[r + currentY][c + currentX] = current[r][c];
            }
          }
        }
      }
      function rotate(dir){
        let offset = 1;
        let kick = 0;
        let newCurrent = [];
        if (dir === 'left') {
          offset = -1;
          kick = -1;
        }
        for (let r = 0; r < current.length; r++){
          newCurrent[r] = [];
          for (let c = 0; c < current[r].length; c++){
            newCurrent[r][c] = current[current.length - c - 1][r];
          }
        }
        if (valid(offset, 0, newCurrent)) {
          current = newCurrent;
          currentX += offset;
        } else if (valid(kick, 0, newCurrent)) {
          current = newCurrent;
          currentX += kick;
        }
      }
      function clearLines(){
        for (let r = 0; r < board.length; r++){
          let rowFilled = true;
          for (let c = 0; c < board[r].length; c++){
            if (board[r][c] === 0) {
              rowFilled = false;
              break;
            }
          }
          if (rowFilled) {
            lines++;
            score += level * 10;
            for (let y = r; y > 1; y--) {
              for (let c = 0; c < 10; c++) {
                board[y][c] = board[y - 1][c];
              }
            }
            for (let c = 0; c < 10; c++) {
              board[0][c] = 0;
            }
          }
        }
      }
      document.addEventListener('keydown', e => {
        if (e.keyCode === 37 && valid(-1, 0)) {
          currentX--;
        } else if (e.keyCode === 38 && valid(0, 0)) {
          rotate('right');
        } else if (e.keyCode === 39 && valid(1, 0)) {
          currentX++;
        } else if (e.keyCode === 40 && valid(0, 1)) {
          currentY++;
        } else if (e.keyCode === 32 && valid(0, 0)) {
          rotate('left');
        }
      });
      newPiece();
      setInterval(() => {
        tick();
        draw();
      }, 1000);
    </script>
  </body>
</html>
Simple HTML Tetris Game with Instructions

原文地址: https://www.cveoy.top/t/topic/lmjL 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录