construindo um jogo para a web bomberman -...

110
Construindo um Jogo para a Web – Bomberman Programação para a Internet Prof. Vilson Heck Junior

Upload: vuongkiet

Post on 28-Jan-2019

238 views

Category:

Documents


0 download

TRANSCRIPT

Construindo um Jogo para a Web – Bomberman

Programação para a InternetProf. Vilson Heck Junior

Tecnologias Necessárias

• Tecnologias já Estudadas:– HTML;

– CSS;

– JavaScript;

• Tecnologias Novas:– Computação Gráfica Básica;

– Noções de Geometria;

– Noções de Física;

– Reprodução de Sons;

– Enredo;

Computação Gráfica

• É um campo da Ciência da Computação que estuda métodos para sintetizar e manipular digitalmente conteúdo visual:– Geração de imagens 2D;

– Geração de imagens 3D (renderização);

– Com ou sem animação;

Noções de Geometria

• Gráficos 2D ou 3D são na verdade a composição de pequenas peças geométricas:

• A relação espacial dada entre diferentes objetos existentes em uma cena deve ser respeitada:

– Dois corpos não podem ocupar um mesmo lugar no espaço!

Noções de Física

• Objetos podem possuir algum tipo de movimento ou interação com outros objetos;

• Para isto, geralmente respeitam alguma(s) regras físicas:

– Próximas a real: Simulação;

– Diferenciadas: Arcade;

Reprodução de Sons

• O som é o elemento responsável por estimular o sentido da audição;

• Não tanto quanto os gráficos, mas os sons são responsáveis por completar uma boa sensação de imersão em jogos e entretenimento;

• Geralmente os sons (músicas ou barulhos) serão escolhidos conforme um determinado contexto ou acontecimento.

Enredo

• O enredo irá explicar ao usuário o que deverá ser feito e deve ser o principal responsável por atrair a atenção do jogador:

– História;

– Diversão;

– Desafios;

– Passatempo;

– ...

Enredo

• Bomberman:– Lançado em 1983;

– Plataforma: PC doméstico;

– Desenvolvido pela Husdson Soft.

Nintendo -1989

Enredo

• Bomberman:– Jogo árcade baseado em labirintos;

– Inimigos não podem te alcançar;

– Destruir paredes e inimigos com bombas.

No

sso

Co

nce

ito

LISTA DE RECURSOS INICIAISBomberman

Recursos Iniciais

• Pasta: “Bomberman”:– index.html

• Construiremos de um documento web, inserindo todos os demais elementos necessários;

– estilo.css

• Definiremos algumas configurações de cores, bordas e outros para nossa interface;

– Bomba.js & bomberman.js & Mapa.js & mapaMascara.js

• Faremos todo o processamento e configurações do jogo, ou seja, daremos ações aos acontecimentos e eventos do jogo.

– Jogador.js & Inimigo.js

• Implementaremos a parte de movimentação do jogador e dos inimigos;

index.html

• Crie o arquivo como doctype para html 5;

• Crie as tags para:

– <html>, <head>, <body> e <title>;

• Estipule um <link> com arquivo de estilo;

• Adicione os arquivos de <script> dentro do <head>:

– mapaMascara.js

– Mapa.js

– Jogador.js

– Inimigo.js

– Bomba.js

• Adicione o arquivo de <script> bomberman.js ao fim do <body>;

– Importante: adicionar os outros arquivos js antes, pois o último precisa dos primeiros já executados.

index.html

• Adicione os seguintes Tags com seus atributos dentro do <body>:

– <canvas>Navegador não suportado!</canvas>

• id = “tela” width=200 height=200

– <button>Iniciar</button>

• onclick=“pausar()” id=“btnIniciar”

– <button>Novo Jogo</button>

• onclick=“reiniciar()” id=“btnNovo”

– <p id="tecla"></p>

– <p>A,S,D,W -> Mover<br>Barra de Espaço -> Liberar bomba</p>

estilo.cssbody { background-color: #224422;

text-align: center; }

#tela {

background-color: black;

border: 2px solid red; }

button {

background-color: #EE9999;

color: white;

border: 1px solid red;

width: 100px;

height: 30px;

font-weight: bold;

cursor: pointer; }

button:hover { background-color: #EEBBBB; }

button:disabled {

background-color: #DDDDDD;

cursor: not-allowed; }

DESENHANDO NO CANVASBomberman

<canvas>

• Canvas é um termo inglês dado a alguns tiposde tela para pintura;

• No nosso caso, será uma área dentro dodocumento HTML onde poderemos pintar oque precisarmos;

• Nosso pincel e paleta de cores estãodisponíveis através de código JavaScript.

<canvas>

• O Canvas é feito para oferecer suporte arápido desenho de cenas bidimensionaisou tridimensionais:

– Geralmente acelerado por Hardware;

0 X width

0 y h

eigh

t

bomberman.js

//Recuperando referência dos objetos no documento

var canvas = document.getElementById("tela");

var ctx = canvas.getContext("2d");

//Um pequeno teste (remover depois de testar)

ctx.fillStyle = "#FF0000"; //Usar cor vermelha

ctx.fillRect(20, 30, 50, 100); //x=20, y=30, w=50 e h=100

Desenhando

• Temos uma tela para desenho;

• Conhecemos uma primeira ferramenta parapintar algo;

• Temos que utilizar esta ferramenta de forma aconstruir o cenário inicial do nosso jogo;

Relembrando

Estrutura de Dados: matriz

Descrição Representação Gráfica Código (cor)

Livre 0 - (preto)

Parede 1 - (branco)

Jogador 2 - (vermelho)

Tijolo 3 - (verde)

Inimigo 4 - (azul)

Bomba 5 - (N/A)

Posições da matriz

Mapa.js

function Mapa() {

//Sem elementos estáticos

}

//Compreensão do conteúdo do mapa

Mapa.LIVRE = 0;

Mapa.PAREDE = 1;

Mapa.JOGADOR = 2;

Mapa.TIJOLO = 3;

Mapa.INIMIGO = 4;

Mapa.BOMBA = 5;

//Linhas e colunas existentes no mapa atual

Mapa.colunas = 0;

Mapa.linhas = 0;

//Largura e altura de cada linha/coluna em pixels

Mapa.largura = 40;

mapaMascara.js

Exemplo de cenário com 5 colunas e 6 linhas:

var mapaMascara =

[ [1, 1, 1, 1, 1],

[1, 0, 2, 0, 1],

[1, 3, 1, 0, 1],

[1, 3, 1, 3, 1],

[1, 3, 4, 0, 1],

[1, 1, 1, 1, 1] ];

Dimensões

• Cada elemento da matriz terá uma largura ealtura, sendo elementos quadrados: largura =altura.

Largura

Dimensões

• A largura, ou altura, geral do jogo, será definida pelalargura de cada elemento x o número de elementos:

AlturaTotal = Largura * nLinhas

Mapa.js

...

//Mantém e carrega o mapa atual

Mapa.atual = null;

Mapa.carregar = function (canvas) {

Mapa.atual = new Array();

var y, x;

for (y = 0; y < mapaMascara.length; y++) {

Mapa.atual.push(mapaMascara[y].slice(0));

}

Mapa.linhas = Mapa.atual.length;

Mapa.colunas = Mapa.atual[0].length;

canvas.width = Mapa.colunas * Mapa.largura;

canvas.height = Mapa.linhas * Mapa.largura;

};

Mapa.js//Carrega textura e desenha mapa

Mapa.imgTijolo = new Image();

Mapa.imgTijolo.src = "tijolo.png";

Mapa.desenhar = function (ctx) {

if (Mapa.atual != null) {

var x, y;

for (y = 0; y < Mapa.linhas; y++) {

for (x = 0; x < Mapa.colunas; x++) {

if (Mapa.atual[y][x] == Mapa.PAREDE) {

ctx.fillStyle = "#BBBBBB";

ctx.fillRect(x * Mapa.largura, y * Mapa.largura, Mapa.largura, Mapa.largura);

} else if (Mapa.atual[y][x] == Mapa.TIJOLO) {

ctx.drawImage(Mapa.imgTijolo, x * Mapa.largura, y * Mapa.largura, Mapa.largura, Mapa.largura);

}

}

}

}

};

bomberman.js

var canvas = document.getElementById("tela");

var ctx = canvas.getContext("2d");

//Adicionar temporariamente. Remover depois.

Mapa.carregar(canvas);

Mapa.desenhar(ctx);

Jogador.js

//Classe para controle e movimentos do jogador

function Jogador() {

}

Jogador.x = -1;

Jogador.y = -1;

Jogador.desenhar = function (ctx) {

ctx.fillStyle = "#00BBBB";

ctx.fillRect(Jogador.x * Mapa.largura + 2, Jogador.y * Mapa.largura + 2, Mapa.largura - 4, Mapa.largura - 4);

};

Mapa.jsMapa.carregar = function (canvas) {

...

for (y = 0; y < mapaMascara.length; y++) {

Mapa.atual.push(mapaMascara[y].slice(0));

for (x = 0; x < Mapa.atual[y].length; x++) {

switch (Mapa.atual[y][x]) {

case Mapa.JOGADOR:

Jogador.x = x;

Jogador.y = y;

break;

}

}

}

...

};

bomberman.js

var canvas = document.getElementById("tela");

var ctx = canvas.getContext("2d");

//Adicionar temporariamente. Remover depois.

Mapa.carregar(canvas);

Mapa.desenhar(ctx);

Jogador.desenhar(ctx);

OS VILÕES!Bomberman

Os Vilões

• No Bomberman, os vilões são “monstros” queandam pelo labirinto;

• Cada mapa terá um número diferente de inimigos.

• Em nossa implementação, cada inimigo será umainstância de uma classe chamada Inimigo;

• Cada vez que encontramos Mapa.INIMIGO nomapa, instanciamos um novo objeto Inimigo.

Inimigo.js

//Classe para controle e movimentos dos inimigos

function Inimigo(x, y, imagem) {

this.x = x;

this.y = y;

this.imagem = imagem;

this.desenhar = function (ctx) {

ctx.drawImage(this.imagem, this.x * Mapa.largura, this.y * Mapa.largura, Mapa.largura, Mapa.largura);

};

}

Construtor

Inimigo.js

//Classe para controle e movimentos dos inimigos

...

Inimigo.todos = new Array();

Inimigo.desenharTodos = function (ctx) {

var i;

for (i = 0; i < Inimigo.todos.length; i++) {

Inimigo.todos[i].desenhar(ctx);

}

};

Mapa.jsMapa.carregar = function (canvas) {

...

switch (Mapa.atual[y][x]) {

case Mapa.JOGADOR:

Jogador.x = x;

Jogador.y = y;

break;

case Mapa.INIMIGO:

var inimigoImg = new Image();

inimigoImg.src = "inimigo.png";

inimigoImg.onload = desenharTudo;

Inimigo.todos.push(new Inimigo(x, y, inimigoImg));

break;

}

bomberman.jsfunction reiniciar() {

Mapa.carregar(canvas);

desenharTudo();

document.getElementById("btnIniciar").disabled = false;

document.getElementById("btnIniciar").innerHTML = "Iniciar";

}

function desenharTudo() {

ctx.clearRect(0, 0, canvas.width, canvas.height);

Mapa.desenhar(ctx);

Jogador.desenhar(ctx);

Inimigo.desenharTodos(ctx);

}

reiniciar();

Testar!

GERAÇÃO DE MAPASBomberman

Geração de Mapas

• Em “Arquivos para Atividades Práticas”

– Na pasta “bomberman”;

– Baixe BombermanMapGenerator.zip;

– Isto é um projeto NetBeans!

• Gerar um arquivo BMP no MS Paint!

– Observar cores que irão definir objetos.

• Converter com o software Java!

Geração de Mapas

• Em “Arquivos para Atividades Práticas”

– Na pasta “bomberman”;

– Baixe “cenario.png” para qualquer pasta

– Converta o arquivo com o Gerador de Mapas baixado anteriormente;

• salve o arquivo gerado com nome mapaMascara.js ;

• Coloque o arquivo gerado dentro da pasta do seu projeto, substituindo o arquivo digitado anteriormente.

Bomberman

• Teste sua página!

COLOCANDO VIDABomberman

O que precisamos?

• Fazer o Bomberman se movimentar ao pressionar de tecla?

• Fazer os inimigos se movimentarem:

– Com qual intervalo de tempo?

– Para qual direção?

• O que acontece se o usuário ordenar que o Bomberman se movacontra uma parede?

• O que ocorre quando o Bomberman liberar uma boba?

• O que ocorre quando o Bomberman encontrar um inimigo?

– E se a bomba explodir perto de um inimigo?

• E quando acabarem todos os inimigos do mapa?

Movimentação do Bomberman

• O Bomberman irá se movimentar conformeteclas que o usuário pressionar:

– A, S, D, W;

– Outras teclas configuradas;

INTERAGINDO COM O USUÁRIOBomberman

Eventos!

• A interação é dada por uma troca entre amáquina e o usuário;

• A máquina fornece principalmenteimagens que descrevem uma situação,onde pode ser necessária a intervençãodo usuário;

• O usuário irá intervir basicamenteatravés de comandos!– Comandos são captados através de eventos.

Eventos!

• Nosso document possui propriedades deeventos que podem ser associadas àfunções quaisquer;

• Estas funções determinam algo a serfeito quando aquele evento ocorrer:

– document.onkeydown

• Ao descer uma tecla qualquer;

– document.onkeyup

• Ao soltar uma tecla qualquer;

document.onkeydown = function (evt) {

document.getElementById("tecla").innerHTML =

evt.keyCode;

}

bomberman.js

Teste!

document.onkeydown = function (evt) {

Jogador.tratarTecla(evt);

}

bomberman.js

Apagar o <p id=“tecla”>

do HTML

Jogador.js

//Configurações de teclas para o Jogador

Jogador.cmdEsq = 65; //A

Jogador.cmdDir = 68; //D

Jogador.cmdCim = 87; //W

Jogador.cmdBai = 83; //S

Jogador.cmdBomba = 32; //Espaço

//Variáveis para controle de movimentação

Jogador.proximoMov = null;

Jogador.plantarBomba = false;

//Tratar tecla pressionado conforme comportamento do Jogador

Jogador.tratarTecla = function (evt) {

switch (evt.keyCode) {

case Jogador.cmdEsq:

case Jogador.cmdDir:

case Jogador.cmdCim:

case Jogador.cmdBai:

Jogador.proximoMov = evt.keyCode;

evt.preventDefault();

break;

case Jogador.cmdBomba:

Jogador.plantarBomba = true;

evt.preventDefault();

break;

}

};

Jogador.js

//Com base no último movimento solicitado, executa movimento

Jogador.mover = function () {

var nx = -1;

var ny = -1;

switch (Jogador.proximoMov) {

case Jogador.cmdEsq:

nx = Jogador.x - 1;

break;

case Jogador.cmdDir:

nx = Jogador.x + 1;

break;

case Jogador.cmdCim:

ny = Jogador.y - 1;

break;

case Jogador.cmdBai:

ny = Jogador.y + 1;

break;

}

Jogador.js (1/3)

if (Jogador.plantarBomba) {

if (Bomba.todas.length < Bomba.maxBombas) {

Bomba.todas.push(new Bomba(this.x, this.y));

}

Jogador.plantarBomba = false;

}

if (nx >= 0 && nx < Mapa.colunas) {

switch (Mapa.atual[Jogador.y][nx]) {

case Mapa.PAREDE:

case Mapa.TIJOLO:

case Mapa.BOMBA:

break;

default:

Jogador.x = nx;

break;

}

}

Jogador.js (2/3)

if (ny >= 0 && ny < Mapa.linhas) {

switch (Mapa.atual[ny][Jogador.x]) {

case Mapa.PAREDE:

case Mapa.TIJOLO:

case Mapa.BOMBA:

break;

default:

Jogador.y = ny;

break;

}

}

Jogador.proximoMov = null;

};

Jogador.js (3/3)

Bomberman

• Colocar temporariamente os comandos dentro, nofim da função Jogador.tratarTecla(evt):

– Jogador.mover();

– desenharTudo();

• Teste sua página!

CONTROLE GLOBAL DO MOVIMENTO

Bomberman

Movendo com Tempo

• Todo tipo de movimento tem uma velocidade;

• Como determinamos a velocidade de algumobjeto?

– Medida Espacial / Tempo!• KM/h

• m/s

• ...

Controlando o Tempo

• Como já definimos, a unidade de espaço de cadamovimento dos inimigos e do jogador será por posição;

• Agora precisamos determinar o intervalo de tempo quenosso jogo irá usar para fazer cada movimento doselementos;

• Como nosso jogo gira em torno do Bomberman e dosInimigos (e cada um terá uma velocidade diferente), estestempos serão como guias para todo o jogo.

Controlando o Tempo

• Função JavaScript:

– relogio = setInterval(“NomeFuncao()”, intervalo);• relogio é uma referência ao timer/clock que foi criado;

• NomeFuncao() é a função que será executada a cada intervalo;

• intervalo é um número inteiro representando a quantidade em milissegundos de intervalo entre uma execução e outra da função NomeFuncao().

– clearInterval(relogio);• Para o relógio de repetição;

bomberman.js

• Crie a variável:

– var intervaloJogador = 200;

– var intervaloInimigos = 400;

• A primeira variável irá definir a quantidade demilissegundos entre cada movimento do Jogador;

• O intervalo entre os movimentos dos inimigos será umpouco maior, para deixá-los mais lentos.

bomberman.js

• Crie as variáveis:

– var tempoJogador = null;

– var tempoInimigos = null;

• Elas serão responsaveis por armazenar a referência aosobjetos que farão a temporização de movimento doJogador e dos Inimigos.

bomberman.js

function reiniciar() {

if (tempoJogador != null) {

pausar();

}

intervaloJogador = 200;

intervaloInimigos = intervaloJogador * 2;

Mapa.carregar(canvas);

desenharTudo();

document.getElementById("btnIniciar").disabled = false;

document.getElementById("btnIniciar").innerHTML = "Iniciar";

//Bomba.todas.length = 0;

//Bomba.maxBombas = 1;

}

bomberman.js

function pausar() {

if (tempoJogador == null) {

tempoJogador = setInterval("atualizaJogador()",

intervaloJogador);

tempoInimigos = setInterval("atualizaInimigos()",

intervaloInimigos);

document.getElementById("btnIniciar").innerHTML = "Pausar";

} else {

clearInterval(tempoJogador);

tempoJogador = null;

clearInterval(tempoInimigos);

tempoInimigos = null;

document.getElementById("btnIniciar").innerHTML =

"Continuar";

}

}

bomberman.js

function atualizaJogador() {

Jogador.mover();

desenharTudo();

}

function atualizaInimigos() {

desenharTudo();

}

Bomberman

• Se você ainda não retirou os seguintes comandos de dentro da função Jogador.tratarTecla(evt), retire:

– Jogador.mover();

– desenharTudo();

• Teste sua página!

MOVIMENTAÇÃO DOS INIMIGOSBomberman

Movimentação dos Inimigos

• Para que os inimigos se movam, precisamosdefinir regras que de alguma formademonstrem coerência no seu movimento;

• Por exemplo:– Não mudar de direção a todo o segundo;

– Ser capaz de eventualmente trocar de direção;

– Não atravessar as paredes;

– Entre outros.

• Antes de mover, o inimigo precisa verificaras possibilidades para onde pode se mover.

Inimigo.js

function Inimigo(x, y, imagem) {

...

this.direcoes = new Array();

this.direcaoAtual = 0;//Parado

...

}

Construtor

Inimigo.jsthis.mover = function () {

this.direcoes.length = 0;

this.adicionaDirecao(this.direcaoAtual, 8);

this.adicionaDirecao(Jogador.cmdCim, 4);

this.adicionaDirecao(Jogador.cmdEsq, 4);

this.adicionaDirecao(Jogador.cmdDir, 4);

this.adicionaDirecao(Jogador.cmdBai, 4);

this.adicionaDirecao(0, 1);//Ficar parado

var aleat = Math.round(Math.random() * (this.direcoes.length -1));

this.direcaoAtual = this.direcoes[aleat];

switch (this.direcaoAtual) {

case Jogador.cmdCim:

this.y--;

break;

case Jogador.cmdBai:

this.y++;

break;

case Jogador.cmdDir:

this.x++;

break;

case Jogador.cmdEsq:

this.x--;

break;

}

};

Inimigo.js (1/2)this.adicionaDirecao = function (dir, vezes) {

var nx = this.x;

var ny = this.y;

switch(dir) {

case Jogador.cmdEsq:

nx--;

break;

case Jogador.cmdDir:

nx++;

break;

case Jogador.cmdCim:

ny--;

break;

case Jogador.cmdBai:

ny++;

break;

} //Fim do switch

Inimigo.js (2/2)

if (nx < 0 || ny < 0 || nx >= Mapa.colunas || ny >= Mapa.linhas) {

return;

}

switch (Mapa.atual[ny][nx]) {

case Mapa.PAREDE:

case Mapa.TIJOLO:

case Mapa.BOMBA:

return;

}

var z;

for (z = 0; z < vezes; z++) {

this.direcoes.push(dir);

}

}; //Fim do adicionaDirecao()

Inimigo.js

//Mover todos os inimigos: método estático!

Inimigo.moverTodos = function() {

var i;

for (i = 0; i < Inimigo.todos.length; i++) {

Inimigo.todos[i].mover();

}

};

bomberman.js

function atualizaInimigos() {

Inimigo.moverTodos();

desenharTudo();

}

Testar!

Alterações Restantes

• O que falta alterar?– INSERIR A BOMBA!

– E quando explode a bomba?• Se atingir o próprio bomberman? Se atingir um inimigo? Se atingir um

tijolo? Se atingir uma parede?

– Fim de jogo?

– Sons?

bomberman.js

function atualizaJogador() {

Jogador.mover();

desenharTudo();

if (Jogador.verificaMorte()) {

gameOver();

}

}

function atualizaInimigos() {

Inimigo.moverTodos();

desenharTudo();

if (Jogador.verificaMorte()) {

gameOver();

}

}

Jogador.js

//Verifica se o Jogador morre (contato com inimigo)

Jogador.verificaMorte = function() {

var i;

for (i = 0; i < Inimigo.todos.length; i++) {

if (Jogador.x == Inimigo.todos[i].x &&

Jogador.y == Inimigo.todos[i].y) {

return true;

}

}

return false;

};

bomberman.js

//Executa comandos para efetuar o gameover

function gameOver() {

if (tempoJogador != null) {

pausar();

}

document.getElementById("btnIniciar").disabled = true;

}

Testar!

A BOMBA!Bomberman

A Bomba• Depois de ser armada (criada), a bomba terá um tempo até a sua explosão;

• Ao explodir, ela irá alcançar um raio, apenas nas quatro direções básicas: cima, baixo,esquerda e direita;

• O raio da explosão pode ser limitado por qualquer objeto que haja no caminho;

• Caso a bomba atinja o Jogador ou algum Inimigo, este deverá morrer;

• Caso a bomba atinja outra bomba, a segunda também deverá explodir imediatamente.

Bomba.jsfunction Bomba(x, y) {

this.x = x;

this.y = y;

this.ciclos = Bomba.nCiclosAtual;

this.cicloAtual = 0;

this.raio = Bomba.raioAtual;

Mapa.atual[y][x] = Mapa.BOMBA;

}

Bomba.som = null;

Bomba.todas = new Array();

Bomba.todas.length = 0;

Bomba.maxBombas = 1; //Valor definido no "novo jogo"

Bomba.nCiclosAtual = 15;

Bomba.raioAtual = 2;

Bomba.nCiclosPos = 2;

Bomba.js (1/5)this.desenhar = function(ctx) {

var raio = Mapa.largura / 2;

var prop = 0.5 + ((0.5 * this.cicloAtual) / this.ciclos);

if (prop > 1) {

prop = 1;

}

ctx.fillStyle = "rgb(" + Math.round(prop * 255) +", " + Math.round(prop * 100) + ", 0)";

if (this.cicloAtual <= this.ciclos) {

ctx.beginPath();

ctx.arc(this.x * Mapa.largura + raio, this.y * Mapa.largura + raio, raio, Math.PI * 2, false);

ctx.closePath();

ctx.fill();

} else {

//Pinta o ponto central da explosão

ctx.fillRect(this.x * Mapa.largura, this.y * Mapa.largura, Mapa.largura, Mapa.largura);

Bomba.js (2/5)} else {

...

var nx, ny, r; //Para cima

for (r = 1; r <= this.raio; r++) {

ny = this.y - r;

if (ny >= 0) {

if (Mapa.atual[ny][this.x] == Mapa.PAREDE) {

break;

} else {

ctx.fillRect(this.x * Mapa.largura, ny * Mapa.largura, Mapa.largura, Mapa.largura);

}

if (Mapa.atual[ny][this.x] == Mapa.TIJOLO) {

break;

}

} //Fecha if (ny >= 0)

} //Fecha for (r)

Bomba.js (3/5)} else {

...

//Para baixo

for (r = 1; r <= this.raio; r++) {

ny = this.y + r;

if (ny < Mapa.linhas) {

if (Mapa.atual[ny][this.x] == Mapa.PAREDE) {

break;

} else {

ctx.fillRect(this.x * Mapa.largura, ny * Mapa.largura, Mapa.largura, Mapa.largura);

}

if (Mapa.atual[ny][this.x] == Mapa.TIJOLO) {

break;

}

} //Fecha if (ny)

} //Fecha for (r)

Bomba.js (4/5)} else {

...

//Para esquerda

for (r = 1; r <= this.raio; r++) {

nx = this.x - r;

if (nx >= 0) {

if (Mapa.atual[this.y][nx] == Mapa.PAREDE) {

break;

} else {

ctx.fillRect(nx * Mapa.largura, this.y * Mapa.largura, Mapa.largura, Mapa.largura);

}

if (Mapa.atual[this.y][nx] == Mapa.TIJOLO) {

break;

}

} //Fecha if (nx)

} //Fecha for (r)

Bomba.js (5/5)//Para direita

for (r = 1; r <= this.raio; r++) {

nx = this.x + r;

if (nx < Mapa.colunas) {

if (Mapa.atual[this.y][nx] == Mapa.PAREDE) {

break;

} else {

ctx.fillRect(nx * Mapa.largura, this.y * Mapa.largura, Mapa.largura, Mapa.largura);

}

if (Mapa.atual[this.y][nx] == Mapa.TIJOLO) {

break;

}

} //Fecha if (nx)

} //Fecha for (r)

} //Fecha o else

}; //Fecha o método desenhar()

Bomba.js

Bomba.desenharTodas = function (ctx) {

var i;

for (i = 0; i < Bomba.todas.length; i++) {

Bomba.todas[i].desenhar(ctx);

}

};

bomberman.js

//REVISAR A FUNÇÃO

function reiniciar() {

if (tempoJogador != null) {

pausar();

}

Mapa.carregar(canvas);

desenharTudo();

document.getElementById("btnIniciar").disabled = false;

document.getElementById("btnIniciar").innerHTML = "Iniciar";

intervaloJogador = 200;

intervaloInimigos = intervaloJogador * 2;

Bomba.todas.length = 0;

Bomba.maxBombas = 1;

}

bomberman.js

//REVISAR A FUNÇÃO

function desenharTudo() {

ctx.clearRect(0, 0, canvas.width, canvas.height);

Mapa.desenhar(ctx);

Bomba.desenharTodas(ctx);

Jogador.desenhar(ctx);

Inimigo.desenharTodos(ctx);

}

Testar!

Bomba.js

Bomba.executarTodosCiclos = function () {

var i;

for (i = 0; i < Bomba.todas.length; i++) {

Bomba.todas[i].executarCiclo();

}

};

Bomba.js

this.executarCiclo = function () {

this.cicloAtual++;

if (this.cicloAtual > this.ciclos) {

if (this.cicloAtual == this.ciclos + 1 && Bomba.som != null) {

//Bomba.som.currentTime = 0;

//Bomba.som.play();

}

//this.explodir();

}

};

bomberman.js

//REVISAR A FUNÇÃO

function atualizaJogador() {

Jogador.mover();

Bomba.executarTodosCiclos();

desenharTudo();

if (Jogador.verificaMorte()) {

gameOver();

}

}

Testar!

Bomba.js (1/5)

this.explodir = function () {

var nx, ny, r, continua;

//Para cima

continua = false;

for (r = 1; r <= this.raio; r++) {

ny = this.y - r;

if (ny >= 0) {

continua = this.verificaEstrago(this.x, ny);

}

if (!continua) {

break;

}

} //Fim do for

Bomba.js (2/5)

//Para baixo

continua = false;

for (r = 1; r <= this.raio; r++) {

ny = this.y + r;

if (ny < Mapa.linhas) {

continua = this.verificaEstrago(this.x, ny);

}

if (!continua) {

break;

}

}

Bomba.js (3/5)

//Para esquerda

continua = false;

for (r = 1; r <= this.raio; r++) {

nx = this.x - r;

if (nx >= 0) {

continua = this.verificaEstrago(nx, this.y);

}

if (!continua) {

break;

}

}

Bomba.js (4/5)

//Para direita

continua = false;

for (r = 1; r <= this.raio; r++) {

nx = this.x + r;

if (nx < Mapa.colunas) {

continua = this.verificaEstrago(nx, this.y);

}

if (!continua) {

break;

}

}

Bomba.js (5/5)

//Garante o tempo da explosão ativa

if (this.cicloAtual > this.ciclos + Bomba.nCiclosPos) {

var posicao = Bomba.todas.indexOf(this);

Bomba.todas.splice(posicao, 1);

Mapa.atual[this.y][this.x] = Mapa.LIVRE;

}

}; //Fim do método explodir()

Bomba.js (1/3)

this.verificaEstrago = function (x, y) {

//Se encontrar uma parede, para o avanço da explosão

if (Mapa.atual[y][x] == Mapa.PAREDE) {

return false;

}

//Se encontrar um tijolo, quebra e para

if (Mapa.atual[y][x] == Mapa.TIJOLO) {

if (this.cicloAtual > this.ciclos + Bomba.nCiclosPos) {

Mapa.atual[y][x] = Mapa.LIVRE;

}

return false;

}

Bomba.js (2/3)

//Se encontrar uma bomba, explode quando for necessário

var i;

for (i = 0; i < Bomba.todas.length; i++) {

if (Bomba.todas[i].x == x &&

Bomba.todas[i].y == y &&

this != Bomba.todas[i] &&

Bomba.todas[i].cicloAtual < Bomba.todas[i].ciclos) {

//Vai explodir

Bomba.todas[i].cicloAtual = Bomba.todas[i].ciclos;

}

}

//Se encontrar o jogador, fim de jogo

if (Jogador.x == x && Jogador.y == y) {

gameOver();

}

Bomba.js (3/3)

//Se encontrar um inimigo, mata-o

i = 0;

while (i < Inimigo.todos.length) {

if (Inimigo.todos[i].x == x && Inimigo.todos[i].y == y) {

Inimigo.todos.splice(i, 1);

} else {

i++;

}

}

return true;

};//Fim do método verificaEstrago()

Bomba.js

this.executarCiclo = function () {

this.cicloAtual++;

if (this.cicloAtual > this.ciclos) {

if (this.cicloAtual == this.ciclos + 1 && Bomba.som != null) {

//Bomba.som.currentTime = 0;

//Bomba.som.play();

}

this.explodir();

}

};

Retirar o comentário

Testar!

ESTÍMULOS SONOROSBomberman

Estímulos Sonoros

• Conforme comentado anteriormente, quanto maisestimularmos, de forma positiva, os sentidos dosjogadores, maior a probabilidade dele se sentircomo parte do jogo;

• Para isto, iremos adicionar alguns pequenos sonsassociados a eventos como colisões;

• Baixe os arquivos e salve na subpasta snd:– bomba.mp_;

– bomba.ogg;

<audio> e <source>

• HTML 5!

• MIME Types:– MP3 – audio/mpeg

– Ogg – audio/ogg

– Wav – audio/wav

• Suporte:– Ps.: Múltiplos <source> fornecem redundância!

Browser MP3 Wav Ogg

IE 9+ Sim Não Não

Chrome 6+ Sim Sim Sim

Firefox 3.6+ Não Sim Sim

Safari 5+ Sim Sim Não

Opera 10+ Não Sim Sim

index.html

...

<audio controls id=“sndBomba">

<source src="snd/bomba.mp_" type="audio/mpeg">

<source src="snd/bomba.ogg" type="audio/ogg">

</audio>

<script src=“bomberman.js"></script>

bomberman.js

//Recuperando referência dos objetos no documento

var canvas = document.getElementById("tela");

var ctx = canvas.getContext("2d");

Bomba.som = document.getElementById("sndBomba");

Bomba.js

this.executarCiclo = function () {

this.cicloAtual++;

if (this.cicloAtual > this.ciclos) {

if (this.cicloAtual == this.ciclos + 1 && Bomba.som != null) {

Bomba.som.currentTime = 0;

Bomba.som.play();

}

this.explodir();

}

}; Retirar os comentários

Testar!

50%

50%

Trabalho1. Customize cores e outras configurações do arquivo de estilo;

2. Customize cores, tamanhos e disposição dos objetos do jogo (dentro doJavascript). Utilize gradientes e/ou imagens;

3. Complete o HTML informando o nome da disciplina, o nome doinstituto e o seu nome, dispondo os elementos com layouts CSS;

4. Existe um bug: quando o jogo não esta em execução, teclaspressionadas são processadas ao retomar o jogo. Corrija este bug.

5. Bug: Ao pressionar o botão “Novo Jogo”, o jogo reinicia mas duplica osInimigos existentes.

6. Crie um placar com pontuação;

7. Crie uma indicação visual dentro do Canvas de fim de jogo;

8. Adicione novos sons a eventos diferentes no jogo;

9. Adicione teclas de atalho para “Pausa” e para “Novo Jogo”;

10. Ao evoluir no jogo, crie novos desafios para o jogador;

– Adicione outros elementos a seu critério;

11. Entregue os arquivos por e-mail ao Professor junto com umadescrição/resposta para cada item do trabalho.