Criando um Jogo Web Whack-a-Mole

JavaScriptBeginner
Pratique Agora

Introdução

Neste projeto, você aprenderá como criar um jogo Whack-a-Mole usando HTML, CSS e JavaScript. O jogo envolve golpear toupeiras que aparecem aleatoriamente de buracos dentro de um limite de tempo especificado. Você criará os arquivos HTML, CSS e JavaScript necessários e implementará a lógica do jogo passo a passo.

👀 Pré-visualização

Whack-a-Mole Web Game

🎯 Tarefas

Neste projeto, você aprenderá:

  • Como configurar os arquivos do projeto para o jogo Whack-a-Mole
  • Como adicionar os estilos CSS necessários para criar o layout e design do jogo
  • Como implementar a lógica do jogo para fazer as toupeiras aparecerem e desaparecerem, manter a pontuação e controlar o tempo
  • Como criar ouvintes de eventos (event listeners) para golpear as toupeiras e iniciar o jogo

🏆 Conquistas

Após concluir este projeto, você será capaz de:

  • Criar arquivos HTML, CSS e JavaScript para um jogo baseado na web
  • Usar CSS para estilizar e criar o layout dos elementos do jogo
  • Manipular o DOM usando JavaScript para fazer os elementos do jogo aparecerem e desaparecerem
  • Lidar com as interações do usuário e atualizar o estado do jogo
  • Usar timers em JavaScript para controlar o tempo e o fluxo do jogo

Criar os arquivos do projeto

Primeiramente, vamos criar os arquivos do projeto para o jogo Whack-a-Mole.

  1. cd para o diretório ~/project.
  2. Crie um novo arquivo chamado index.html.
  3. Copie e cole o seguinte código em index.html:
<!doctype html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <link
      href="https://cdn.jsdelivr.net/npm/tailwindcss@2.2.19/dist/tailwind.min.css"
      rel="stylesheet"
    />
    <link rel="stylesheet" href="styles.css" />
    <title>Whack-a-Mole!</title>
  </head>

  <body
    class="bg-gradient-to-r from-yellow-400 via-red-500 to-pink-500 flex items-center justify-center h-screen"
  >
    <div class="game bg-white p-8 rounded-lg shadow-2xl text-center">
      <h1 class="text-4xl font-bold mb-4 text-red-600">Whack-a-Mole!</h1>
      <p class="score text-2xl text-red-600">
        Score: <span id="score">0</span>
      </p>
      <p class="time text-2xl text-red-600">
        Time Left: <span id="time">0</span>
      </p>
      <button
        id="startBtn"
        class="bg-red-500 hover:bg-red-700 text-white font-bold py-2 px-4 rounded mt-4 transition duration-500 ease-in-out transform hover:-translate-y-1 hover:scale-110"
      >
        Start Game
      </button>
      <div id="grid" class="grid grid-cols-3 gap-4 mt-4">
        <!-- Holes will be added here -->
      </div>
    </div>
    <script src="main.js"></script>
  </body>
</html>

Adicionar os estilos CSS

  1. Crie um novo arquivo chamado styles.css.
  2. Copie e cole o seguinte código em styles.css:
.game {
  width: 600px;
  border-radius: 2rem;
}

.hole {
  height: 0;
  padding-bottom: 100%;
  position: relative;
  background: #eee;
  border: 3px solid #ccc;
  border-radius: 50%;
  overflow: hidden;
}

.mole {
  width: 100%;
  height: 100%;
  background: #a0522d;
  border-radius: 50%;
  position: absolute;
  transform: translateY(100%);
  transition: transform 0.3s;
}

.mole.up {
  transform: translateY(0);
}

.mole.whacked {
  background: #008cff;
}

#startBtn {
  background-color: #0051ff;
  color: #fff;
  padding: 10px 20px;
  border-radius: 20px;
  border: none;
  cursor: pointer;
  transition: background-color 0.3s;
}

#startBtn:hover {
  background-color: #028a5f;
}

Adicionar a lógica do jogo

  1. Crie um novo arquivo chamado main.js.
  2. Adicionaremos o código JavaScript nos passos subsequentes.

Agora, vamos adicionar a lógica do jogo ao arquivo main.js.

  1. Abra o arquivo main.js.
  2. Copie e cole o seguinte código em main.js:
const grid = document.querySelector("#grid");
const scoreDisplay = document.querySelector("#score");
const timeDisplay = document.querySelector("#time");
const startBtn = document.querySelector("#startBtn");
let holes = [];
let score = 0;
let lastHole;
let timeUp = false;
let gameTimer;
let countdownTimer;
let countdown;

function createHoles() {
  for (let i = 0; i < 6; i++) {
    const hole = document.createElement("div");
    const mole = document.createElement("div");

    hole.classList.add("hole");
    mole.classList.add("mole");

    hole.appendChild(mole);
    grid.appendChild(hole);

    holes.push(hole);
  }
}

function randomTime(min, max) {
  return Math.round(Math.random() * (max - min) + min);
}

function randomHole(holes) {
  const idx = Math.floor(Math.random() * holes.length);
  const hole = holes[idx];
  if (hole === lastHole) {
    return randomHole(holes);
  }
  lastHole = hole;
  return hole;
}

function peep() {
  // TODO: Implement this function in Step 3.
}

function startGame() {
  // TODO: Implement this function in Step 4.
}

function whack(e) {
  // TODO: Implement this function in Step 5.
}

createHoles();
// TODO: Implement the rest of the code in Step 6.

Este código define variáveis para armazenar referências a vários elementos HTML e inicializa outras variáveis necessárias. Ele também define várias funções para criar buracos (holes), gerar tempos e buracos aleatórios, fazer com que as toupeiras (moles) apareçam e desapareçam, iniciar o jogo e lidar com os "whacks" nas toupeiras. Finalmente, ele cria os buracos, adiciona ouvintes de eventos aos buracos e configura o ouvinte de eventos de clique do botão de início.

Implementar a função 'peep'

Neste passo, implementaremos a função peep, que faz com que as toupeiras (moles) apareçam e desapareçam aleatoriamente.

  1. Abra o arquivo main.js.
  2. Localize a função peep.
  3. Substitua o código existente pelo seguinte código:
function peep() {
  const time = randomTime(200, 1000);
  const hole = randomHole(holes);
  hole.querySelector(".mole").classList.add("up");

  setTimeout(() => {
    hole.querySelector(".mole").classList.remove("up");
    hole.querySelector(".mole").classList.remove("whacked");
    if (!timeUp) peep();
  }, time);
}

Esta função define um intervalo de tempo aleatório entre 200ms e 1000ms usando a função randomTime. Ela seleciona um buraco (hole) aleatório usando a função randomHole e faz com que a toupeira (mole) apareça adicionando a classe up ao elemento da toupeira. Após o intervalo de tempo especificado, a toupeira desaparece removendo a classe up. Se o jogo não acabou (timeUp é false), a função chama a si mesma recursivamente para fazer com que outra toupeira apareça.

Implementar a função startGame

Em seguida, implementaremos a função startGame, que inicializa o jogo e inicia o temporizador.

  1. Abra o arquivo main.js.
  2. Localize a função startGame.
  3. Substitua o código existente pelo seguinte código:
function startGame() {
  scoreDisplay.textContent = 0;
  timeUp = false;
  score = 0;
  peep();
  gameTimer = setTimeout(() => (timeUp = true), 10000);
  countdown = 10;
  timeDisplay.textContent = countdown;
  startBtn.disabled = true;
  countdownTimer = setInterval(() => {
    countdown--;
    if (countdown < 0) {
      clearInterval(countdownTimer);
      startBtn.disabled = false;
      return;
    }
    timeDisplay.textContent = countdown;
  }, 1000);
}

Esta função inicializa a pontuação, define timeUp como false e redefine a exibição da pontuação. Ela chama a função peep para iniciar as aparições das toupeiras. Ela inicia um temporizador do jogo usando setTimeout para definir timeUp como true após 10 segundos. Ela também configura um temporizador de contagem regressiva para atualizar a exibição do tempo a cada segundo. A contagem regressiva é inicialmente definida como 10 e, quando atinge 0, o temporizador de contagem regressiva é limpo, o botão de início é habilitado e a função retorna.

Implementar a função 'whack'

Agora, vamos implementar a função whack, que lida com o ato de "whackar" (bater) nas toupeiras e atualizar a pontuação.

  1. Abra o arquivo main.js.
  2. Localize a função whack.
  3. Substitua o código existente pelo seguinte código:
function whack(e) {
  if (!e.isTrusted || !this.querySelector(".mole").classList.contains("up"))
    return; // fake click detected or the mole is not up
  score++;
  this.querySelector(".mole").classList.remove("up");
  this.querySelector(".mole").classList.add("whacked");
  scoreDisplay.textContent = score;
}

Esta função é chamada quando uma toupeira é clicada. Ela verifica se o evento de clique é confiável (e.isTrusted) para evitar cliques falsos. Ela também verifica se a toupeira está atualmente "up" (aparecendo) verificando se ela possui a classe up. Se o clique for válido, ela incrementa a pontuação, remove a classe up do elemento da toupeira, adiciona a classe whacked para indicar visualmente que a toupeira foi "whackada" (atingida) e atualiza a exibição da pontuação.

Inicializar o jogo e os event listeners

Nesta etapa, inicializaremos o jogo criando os buracos (holes) e adicionando ouvintes de eventos aos buracos e ao botão de início.

  1. Abra o arquivo main.js.
  2. Localize a linha com a chamada da função createHoles().
  3. Adicione o seguinte código após a chamada da função createHoles():
holes.forEach((hole) => hole.addEventListener("click", whack));

startBtn.addEventListener("click", startGame);

Este código adiciona um ouvinte de evento de clique a cada elemento de buraco (hole). Quando um buraco é clicado, a função whack é chamada. Ele também adiciona um ouvinte de evento de clique ao botão de início, que chama a função startGame quando clicado.

Testar o jogo Whack-a-Mole

Clique no botão Go Live no canto inferior direito do WebIDE e mude para a aba Web 8080.

Botão Go Live do WebIDE

Isso abrirá o projeto na aba Web 8080.

Visualização da aba Web 8080

Resumo

Neste projeto, criamos os arquivos do projeto para o jogo Whack-a-Mole. Criamos a estrutura HTML, adicionamos estilos CSS e implementamos a lógica do jogo usando JavaScript. Os próximos passos envolveriam a personalização e aprimoramento adicionais do jogo, como adicionar sons, níveis e configurações de dificuldade.

✨ Verificar Solução e Praticar✨ Verificar Solução e Praticar✨ Verificar Solução e Praticar✨ Verificar Solução e Praticar✨ Verificar Solução e Praticar✨ Verificar Solução e Praticar✨ Verificar Solução e Praticar✨ Verificar Solução e Praticar