Desenvolvimento de jogos com HTML5 O HTML 5 é uma nova plataforma para o desenvolvimento de jogos online e com potencial para ser uma das mais utilizadas para o desenvolvimento de jogos, pois esta linguagem é compatível com a maioria dos browsers existentes em computadores, tablets e smartphones, incluindo iPads e iPhones. Utilizando o HTML 5 juntamente com as folhas de estilos CSS e o JavaScript é possível desenvolver jogos de uma forma rápida, compatível com diversas plataformas, incluindo dispositivos móveis (como já descrito acima), o que não possível com plataformas como Adobe Flash, onde é necessário realizar adaptações para que o mesmo jogo seja executado em diferentes dispositivos. Mais antes de iniciar a aprendizagem do HTML 5 é importante saber quais são os profissionais envolvidos no desenvolvimento de jogos e quais as etapas presentes neste desenvolvimento. O que é um Jogo? Um jogo é uma atividade lúdica (toda e qualquer ação que tem como objetivo produzir prazer quando é executada) composta por uma série de ações e decisões, limitado por regras e pelo universo do jogo, que resultam em uma condição final. Já os jogos digitais, as regras e o universo do jogo são m apresentados por meios eletrônicos e controlados por um programa digital. As ações do jogador, suas decisões, escolhas e oportunidades compõem a "alma do jogo". Antes de iniciar o desenvolvimento de um jogo, vamos conhecer quais são os profissionais envolvidos neste desenvolvimento. Profissionais envolvidos na criação de jogos Além de uma plataforma de desenvolvimento de jogos são necessários profissionais de várias áreas para a criação do jogo. Entre eles podemos destacar: Produtores: são os responsáveis por supervisionar o desenvolvimento de um jogo. Os produtores são responsáveis em dar vida à ideia inicial de um jogo. Game Designers: Os profissionais responsáveis desta área são os responsáveis pela criação e participam da concepção de ideias para o desenvolvimento. Dentro da criação de um jogo existem vários tipos de Designers, como por exemplo: Character Designer: Responsável pela criação dos personagens do jogo. Game Designer: É o responsável pela jogabilidade, ambiente e história durante a produção do jogo. Object Designer: É o responsável pela criação dos elementos do cenário, personagens e como eles irão se interagir entre si. Level Designer: É o responsável pela criação dos desafios, puzzles (quebra-cabeças) e é claro o desenvolvimento das fases do jogo. Sound Designer: É o responsável pela criação dos sons e as músicas executadas no jogo. Modeladores 3D: Criam e modelam em 3D todos os personagens do cenário, da animação, criam texturas, iluminação, dentre tantas outras que envolvam imagem. Neste curso apenas criaremos jogos utilizando imagens em 2 dimensões, não sendo necessário conhecimento de ferramentas 3D. Programadores: são os responsáveis por desenvolver toda a lógica do jogo e criar o código que irá fazer funcionar a física do jogo. Programador de física do jogo: dedica-se ao desenvolvimento da física que o jogo irá utilizar, estabelecendo regras que simularão a gravidade. Programador de inteligência artificial: São os responsáveis por desenvolver toda a lógica existente por detrás de cada ação que é feita durante o jogo. Programadores de gráficos: São os responsáveis por não deixar jogo lento quando, por exemplo, há muitos inimigos na tela, o que exige uma grande capacidade de processamento, às vezes superior ao que o console ou computador suportam. São os responsáveis por otimizar a maneira como os gráficos serão apresentados na tela. Testadores: são os responsáveis por analisar tecnicamente o jogo com o objetivo de indicar falhas em seu desenvolvimento. O foco deste curso é o desenvolvimento de jogos em HTML5, sendo assim, iremos focar o curso no conhecimento da linguagem HTML5. As imagens, o roteiro do jogo e os demais elementos presentes no jogo já estão prontos, bastando apenas desenvolver, ou seja, entraremos na fase de produção do jogo. Vamos então conhecer quais desenvolvimento de um jogo. são as fases de Etapas na produção de um jogo Agora que você já conhece os profissionais envolvidos na criação de um jogo, vamos agora conhecer as etapas da produção de um jogo. Pré-produção: A pré-produção de um jogo envolve elementos de concepção de ideia, regras de negócios e documentação do projeto. Para que um jogo comece a ser produzido, as ideias precisam ser criadas e aprovadas pelos editores e desenvolvedores da empresa. Produção: Nesse estágio de produção os programadores trabalham para desenvolver a lógica do jogo, bem como os sistemas de cálculo, de física etc. Os artistas se concentram na produção de personagens, hoje em dia todos modelados em 3D. Engenheiros de som desenvolvem os efeitos sonoros e os compositores a trilha sonora do jogo. Pós-Produção: É nesta fase em que os testadores trabalham testando o jogo à busca não só de bugs (erros), mas também testando a jogabilidade, desempenho computacional das plataformas com o jogo e tudo o mais. Após a realização de todos os testes e a obtenção de garantia que o jogo está totalmente pronto, a logística de distribuição e venda é acionada para que o jogo seja vendido. Ambiente de trabalho Agora que conhecemos as etapas na produção de um jogo, vamos preparar o ambiente de trabalho para a produção de um jogo emHTML5. Para a criação de códigos HTML5, CSS e JavaScript não são necessários à instalação de nenhum aplicativo específico, pode-se até utilizar o bloco de notas do Windows, mas para um desenvolvimento mais preciso, e para que se possa realizar testes de maneira mais confiável, iremos utilizar neste curso os seguintes aplicativos. Notepad++ Notepad++ é um software livre (como em "liberdade de expressão" e também como em "cerveja grátis") editor de código fonte e substituição bloco de notas que suporta várias línguas. Em execução no ambiente MS Windows, o seu uso é regido pela licença GPL. Com base na poderosa edição componente Scintilla, Notepad++ é escrito em C++ e usa puro Win32 API eSTL, que garante uma maior velocidade de execução e menor tamanho do programa. Para abrir o programa, clique no menu Iniciar, escolha Todos os Programas, selecione a pasta Notepad++ e por fim clique sobre Notepad++. Editor Notepad++ aparece na tela. Caso seu computador no possua o Notepad ++, você pode baixá-lo a partir da URL: http://notepad-plus-plus.org Google Chrome Canary e Mozilla Firefox O Google Chrome Canary é um browser que tem como finalidade funcionar como teste de desenvolvimento, pois ele apresenta funcionalidades que ainda não foram aplicadas na versão estável para o público geral. Em outras palavras, ele é uma versão para desenvolvedores, ele é hoje uma versão que será estável num futuro próximo (dias ou meses). A diferença dessa versão em relação à versão estável (pública) é o maior suporte às APIs e funcionalidades do HTML5. Você pode baixa-lo a desta URL:https://tools.google.com/dlpage/chromesxs/ partir O Mozilla Firefox, ao lado do Chrome, é um dos navegadores mais populares da internet e também é totalmente compatível com os principais recursos do CSS3. Você pode baixa-lo a partir desta URL:http://www.mozilla.org/ptBR/firefox/fx/ Agora que já temos os programas necessários, vamos conhecer os conceitos básicos da linguagem HTML5. Conhecimentos básicos sobre HTML5, CSS e JavaScript No desenvolvimento de jogos ou qualquer aplicativo utilizando o HTML5, alguns mitos de desenvolvimento devem ser explicados. A estrutura de desenvolvimento de um aplicativoHTML5 segue as seguintes características: HTML5 - Marcação. CSS - Formatação. JavaScript - Comportamento. O que isso quer dizer? Ao se criar um jogo ou aplicativo utilizando HTML5, o HTML5 somente será responsável pela exibição dos elementos no browser, como imagens, textos, execução de sons, exibição de vídeos etc. Para realizar a formatação desses objetos iremos utilizar o CSS e para criar comportamentos e funções, ou seja, a programação do aplicativo, utilizaremos o Java Script. O HTML5 não apresenta métodos e funções para detecção de comportamentos, isso deve ser feito em JavaScript. O que o HTML5 trouxe de novo são as novas possibilidades para que o Javascript controle os elementos criados no código. Então vamos agora conhecer um pouco de cada uma dessas linguagens. Vamos agora relembrar os conceitos básicos de cada uma das linguagens que serão utilizadas neste curso. HTML 5 O HTML5 é o novo padrão da linguagem de marcação de hipertextos (HTML). Apesar de o HTML5 ainda estar em fase de desenvolvimento, a maioria de seus novos recursos já podem ser utilizados em browsers modernos como o Google Chrome, Mozilla Firefox, Safari etc. O que é há de novo no HTML5 e quais as vantagens de sua utilização: Elemento para desenho 2D. Elementos < audio > e < video > para reprodução de mídias. Suporte para armazenamento local. Novos elementos semânticos: < article >, < header >, < foot >, < section >, etc. Novos controles de formulários, como calendários, data, hora, pesquisa, telefone etc. Vamos agora criar uma estrutura básica de um códigoHTML5 no Notepad++ instalado anteriormente. Abra-o, caso ainda não esteja. Clique no menu Arquivo e depois em Novo: Como vamos trabalhar com a linguagem HTML, precisamos informar ao Notepad++, a linguagem que iremos trabalhar, para isto, clique no menu Linguagem, selecione a letra H e clique em HTML. Defina para o arquivo aberto a seguinte marcação HTML: exemplo1.html Esta é a estrutura básica de uma página em HTML5. Vamos entender suas principais partes à seguir. O Doctype O Doctype deve ser sempre a primeira linha de código do documento antes da tag HTML: O Doctype indica para o navegador e para outros meios qual a especificação de código utilizada, que nesse caso, é HTML5. Isso determina a forma com que o meio de acesso (navegador, leitor de tela e etc) irá renderizar o código lido. O Doctype não é uma tag do HTML, mas uma instrução para que o browser tenha informações sobre qual versão de código a marcação foi escrita. O elemento HTML Uma marcação (código) HTML é uma série de elementos em árvore onde alguns elementos são filhos de outros e assim por diante (DOM). O elemento principal dessa grande árvore é sempre o . O atributo "lang" é necessário para identificar qual a linguagem principal do documento. Vamos agora salvar este arquivo. Clique no menu Arquivo em seguida selecione a opção Salvar. Para o local de gravação, escolha a Sua Pasta. Crie uma pasta com o nome de jogo1, dentro de sua pasta. Salve o arquivo com o nome deexemplo1.html na pasta jogo1, recém-criada: Vamos agora testar o funcionamento do código diretamente no browser. Clique no menu Executar do NotePad++ e escolha a opção, Launch in Chrome. Observe que o no browser padrão. resultado do código será apresentado Vamos agora aplicar um formato ao seletor < h1 > utilizado no código HTML utilizando as folhas de estilo CSS. Folhas de estilo CSS CSS é a abreviação do termo em inglês Cascading Style Sheet que é traduzido para o português como folhas de estilo em cascata. O CSS tem por finalidade indicar como uma determinada marcação em HTML/XML deve ser exibido, como por exemplo, cor, tamanho, posição, etc. Segundo a W3C (World Wide Web Consortium) que é um consórcio internacional de pessoas e empresas e órgãos governamentais que visa desenvolver padrões para a criação e a interpretação de conteúdos para a Web, CSS pode ser definida da seguinte maneira: "CSS é um mecanismo simples para adicionar estilos, por exemplo, fontes, cores, espaçamentos aos documentos web". Vamos conhecer a estrutura básica de uma regra CSS. Anatomia de uma regra CSS Na imagem abaixo tempos uma regra básica da anatomia de um código CSS, que deve ser composta pelo seletor e a declaração que será atribuída a esse seletor, composta por propriedade e valor: Seletor: Alvo da regra CSS. Elemento ou grupo de elementos que receberão os estilos definidos na regra. Declaração: Parâmetros de estilização. Propriedade: Define qual será a característica do seletor a ser utilizada. Valor: É a qualidade ou a quantificação da propriedade. O código CSS deve ser escrito entre as tags < style > e< /style > do código HTML. Vamos alterar as propriedades CSS do seletor < h1 >. No exemplo acima alteramos as propriedades fontsize para 30px e a propriedade color para blue. Vamos agora alterar as propriedades para o seletor div identificado com o nome "objeto1". Salve o arquivo no Notepad++, logo seu browser. Visualização do arquivo: após visualize-o no Pressione [CTRL+S] (para salvar) e teste o funcionamento do código: Observe que a formatação do seletor < h1 >foi alterada e a div objeto1 foi formatada e posicionada respeitando as propriedades indicadas. JavaScript JavaScript é uma linguagem de programação com recursos embutidos para acessar partes de um documento HTML, incluindo estilos CSS dentro dos elementos. Um documento HTML pode conter código JavaScript dentro do elemento < script >. Vamos realizar um exemplo simples, vamos exibir a data atual por um código JavaScript. Pressione [CTRL+S] para salvar as alterações no documento. Abra o arquivo no Browser e visualize o resultado apresentado: O método document.write escreve qualquer informação no documento, neste exemplo indicamos a informação que deveria ser escrito era a data e hora atual obtidas pela função Date(). Caso queira escrever uma mensagem no documento pelo método document.write é obrigatório o uso das aspas como o exemplo abaixo: Não utilize aspas para exibir valores numéricos, funções e conteúdo de variáveis. Vamos agora alterar propriedades CSS pelo código Javascript. Funções JavaScript definidas pelo programador O JavaScript possui muitas funções e métodos embutidos, mas não possui tudo o que você poderia precisar no desenvolvimento de um aplicativo e principalmente de um jogo, por isso é possível criar funções especificas. Inicialmente vamos código JavaScript. criar a div que será alterada pelo Como exemplo vamos criar uma função que irá alterar a propriedade background-color da div objeto1. Exclua a linha de código com o método document.writer e digite o código abaixo: Observe que criamos uma função com o nome de mudar Cor que pelo método document.getElmentByid irá alterar a propriedade backgroundColor da div identificada nome objeto1 para verde. pelo Agora vamos criar um botão irá executar essa função. Pressione [CTRL+S] para salvar as alterações no documento e execute-o: jQuery Quando se trata da complexidade de programar jogos, o ideal é que se tente simplificar e facilitar a utilização do código. Para isso, existem hoje FrameWorks JavaScript que ajudam o desenvolvedor a abstrair uma grande quantidade de código, como por exemplo, resolver problemas de compatibilidade entre browsers entre outras funções. O jQuery é hoje um dos FrameWorks mais utilizados para o desenvolvimento de jogos e de outros demais aplicativos utilizando o HTML5. Link para a última versão estável dojQuery: http://code.jquery.com/jquery.min.js disponível Temos duas opções: Usar essa URL de um servidor externo (Google Code) nos exemplos. Baixar esse arquivo jquery.min.js e colocar localmente em uma pasta para usarmos. Para este curso, vamos escolher a primeira opção, vamos usar essa URL direta do jQuery que está hospedado no Google Code. Antes, crie um botão que irá chamar uma função com o nome de ocultar(). Digite o código abaixo após a tag < input > criada anteriormente: Vamos agora criar a código abaixo entre < /script >: função ocultar(). Digite as tags < script > o e Observe que agora o código foi simplificado de tal forma que apenas precisamos utilizar o caractere $ e indicar o nome do objeto a ser modificado e a propriedade que será utilizada. Mas para usar esta forma simplificada devemos informar no código que iremos utilizar o framework jQuery. Digite o código abaixo após a tag < /title > antes de < style >: Pressione [CTRL+S] para salvar as alterações no documento. Veja o resultado final do documento: Nada impede que você crie uma pasta, por exemplo, chamada js dentro da pasta jogo1 e salve o arquivo do jQuery lá, e ao chama-lo usando a tag < script >: Isso vai ficar a seu critério. Abra o arquivo no Browser e visualize o resultado apresentado. Observe que ao clicar no botão "Ocultar div" adiv será oculta. Agora que já revimos alguns conceitos básicos de HTML, JavaScript e CSS vamos dar inicio ao primeiro jogo. Documento do Projeto do Jogo Embora muitas pessoas saltem esta etapa no desenvolvimento de jogos, ela é uma parte essencial do processo do desenvolvimento de um jogo. O documento do jogo determina por escrito todo o rascunho do jogo, descrevendo as peças que deverão se juntar para formar o game, incluindo: Resumo do tema ou enredo; Lista de locações ou ambientes que o jogo irá conter; Rascunhos de mapas, puzzles a serem solucionados; Elenco de personagens, storyboard com as animações entre outras informações. É claro que os tipos e a quantidade de informações que esse documento irá conter dependem do tamanho e da complexidade do jogo. Observação: O início deste jogo será desenvolvimento utilizando exclusivamente JavaScript e CSS. Nas unidades que se seguem iremos complementá-lo com recursos do HTML5, com o áudio e armazenamento local, por exemplo. É importante criar esse primeiro exemplo para que você conheça os principais recursos de desenvolvimento de jogos, como detecção de teclas, detecção da posição do mouse, identificações de colisões, etc. Vamos então ao documento deste Projeto: Nome do jogo: Pong. Tema: Jogo para 2 jogadores onde a missão dos jogadores é rebater um asteroide: Fazendo com que o seu adversário não alcance o asteroide e assim acumular pontos. Será somado 1 ponto quando o asteroide atingir a área de pontuação: Os jogadores irão controlar os rebatedores: Pelas seguintes teclas: Jogador 1: W - movimenta o rebater para cima. S - movimenta o rebater para baixo. Jogador 2: Seta para cima - movimenta o rebatedor para cima. Seta para baixo - movimenta o rebatedor para baixo. O jogo se passará no espaço, portanto iremos utilizar como imagem de fundo uma imagem espacial: Observe que esse documento, apesar de bem simples, facilita o entendimento do programador para um desenvolvimento mais rápido, e também evita possível erros de entendimento de como será a mecânica do jogo. Com base neste documento vamos dar início ao desenvolvimento do jogo. Criando o Jogo Abra o aplicativo Notepad++ e crie um novo documento, clicando em Arquivo e depois em Novo. Digite a estrutura básica de um código HTML como indicado baixo: “pong.html” Iremos iniciar o desenvolvimento do jogo criando o código CSS que irá formatar e posicionar as divs que serão utilizadas no jogo. Vamos iniciar criando uma div com o tamanho de 600pixels de largura por 400 pixels de altura que irá receber a imagem de fundo do jogo. Iremos chamar essa div de fundo. Abaixo da div fundo iremos indicar a formatação de uma div com o nome de asteroide. Agora, iremos criar uma classe com o nome de paddle que irá posicionar os batedores laterais que serão controlados pelos jogadores. Para finalizar o posicionamento dos elementos do jogo vamos criar uma div com o nome depaddle2 que irá posicionar o rebatedor da direita. Com o código CSS indicamos o posicionamento e a formatação dos objetos, vamos agora, criar o código HTML que irá criar os objetos. Observe que todas as divs criadas estão posicionadas dentro de uma div container chamada de fundo. Antes de visualizar o resultado do jogo, copie a pasta pong que se encontra em \arquivos-cursos\html5, para Sua pasta, nela estão os arquivos de imagens e sons que serão utilizados neste jogo. Vamos agora visualizar o resultado. Pressione comando [CTRL+S] para salvar as alterações no arquivo. o Salve este arquivo com o nome de pong.htmldentro pasta jogo1, que se encontra dentro de sua pasta. da Abra o arquivo pong.html no Chrome e veja o resultado: A partir do próximo tópico iremos criar o código JavaScript que irá alterar a posição das divspaddle1 e paddle2 quando as teclas de movimentação do jogo forem pressionadas pelos jogadores. Capturando as teclas pressionadas Com base no documento do jogo criado na aula anterior iremos agora capturar as teclas que serão pressionadas pelo jogador1 para movimentar o batedor. A criação de uma função que captura as teclas pressionadas pelo jogador é uma das funções mais importantes no desenvolvimento de um jogo. Sabemos pelo documento do jogo que o jogador1 irá pressionar as teclas W e S para movimentar o batedor. O JavaScript identifica a tecla pressionada pelo seu valor Decimal (DEC) na tabela ASCCII, que pode ser consultada no link: http://www.asciitable.com/ Após identificar a tecla que jogador1 irá pressionar, devemos indicar qual será o comportamento a ser executado. Quando ojogador1 pressionar a tecla W (código decimal 87) a divpaddle1 será movimentada -5 pixels no eixo Y. Caso ojogador1 pressione a tecla S (código decimal 83) a divpaddle1 será movimentada +5 pixels no eixo Y. Com base nessas informações a primeira coisa a fazer é criar uma variável com os códigos decimais de cada tecla que será capturada. Diferentemente no exemplo criado na unidade anterior, nesta unidade iremos criar um arquivo específico para o código JavaScript. Abra o aplicativo Notepad++ e crie um novo documento em branco. Digite nele apenas o código JavaScript abaixo: “pong.js”. Dentro da pasta jogo1, crie uma pasta chamada js e salve esse arquivo desta pasta js com o nome de pong.js. A pasta jogo1 ficará com essa estrutura: Agora vamos criar uma função que irá identificar se as teclas W ou S serão pressionadas. Utilizamos a estrutura condicional switch para identificarmos quando as teclas forem pressionadas. Quando o usuário digitar "W" o elemento paddle1 terá sua propriedade top alterada, incrementada em 5. Quando apertar "S" terá a propriedade top decrementada em 5. Pressione [CTRL+S] para salvar as alterações no arquivo. Abra o exemplo no navegador e pressione as teclas "W" e "S". Capturando eventos de mouse Vamos supor que no documento de desenvolvimento deste jogo ao invés de estar descrito que os rebatedores serão controlados pelas teclas do teclado, os rebatedores deverão ser controlados pelo mouse. Neste caso, devemos capturar as posições Y do ponteiro do mouse e alterar a posição da propriedade top da div #paddle1. Vamos criar um novo arquivo JavaScript onde iremos criar um evento, que irá capturar a posição Y do ponteiro do mouse. Crie um novo arquivo em branco no Notepad. Iremos agora criar um evento com o nome de coordenadas e iremos criar uma nova variável com o nome de y. Existem diferenças entre capturar a posição do ponteiro do mouse entre o Google Chrome e entre o Mozilla Firefox. Para que este jogo possa funcionar corretamente nestes dois tipos de browsers, fizemos essa verificação: Indicamos que a propriedade top da div#paddle1 deverá ser atualizada de acordo com a posição do eixo Y do mouse menos 80unidades que a altura total da div #paddle1. Desta fora, o ponto de referência para a movimentação da div#paddle1 estará posicionado no topo da div: Observe que finalizamos a função e indicamos que caso o mouse se movimente no browser a função coordenadas será executada: Salve este arquivo de pong_mouse.js. Vamos agora arquivo pong.html. dentro vincular da o pasta js com o nome arquivo pong_mouse.jsao Abra o arquivo pong.html e substitua o arquivo pong.js pelo arquivo pong_mouse.js: Pressione [CTRL+S] para salvar as alterações no arquivo. Abra o arquivo no navegador e veja o resultado. Criando a movimentação do segundo jogador Nesta unidade iremos voltar a seguir o documento do jogo. Observe que no documento do jogo, o jogador2 irá movimentar o rebatedor pelas setas de direção. Quando o jogador2 pressionar a seta para cima do teclado, a div paddle2 irá se movimentar -5 pixels no eixo Y. Quando o jogador2 pressionar a seta para baixo do teclado a div padlle2 irá se movimentar +5 pixels no eixo Y. Abra o arquivo pong.html e remova a referência arquivo pong_mouse.js e substitua pelo arquivo pong.js: ao Pressione [CTRL+S] para salvar as alterações no arquivo. Abra o arquivo pong.js. Na variável TECLA indicaremos os códigos para a seta para cima (38) e seta para baixo (40). Agora ela terá essa implementação: Também vamos acrescentar a ação para o elemento Paddle2. O código completo de pong.js Uma observação muito importante relacionada ao novo código: Armazenaremos a referência dos elementos em variáveis: E depois as usamos. Ganhamos em performance ao fazer isso, pois o JavaScript só precisa procurar na árvore DOM pelos elementos apenas uma vez. Se tivéssemos feito assim (não precisava alterar o código): Iria funcionar normalmente. Mas ficaria um código deselegante e de difícil alteração. Além disso, a cada $("#paddle2") e$("#paddle1") o JavaScript teria que pesquisar o elemento na árvore DOM, o que decrementa a performance (apesar dela ser imperceptível para este pequeno projeto). Game Loop O Game Loop é o loop principal do jogo, em alguns casos, chamado de seu coração. Ele é responsável pelo funcionamento do jogo. Em um exemplo clássico, um jogo consiste de uma sequência de pegar a entrada do usuário, atualizar o estado do jogo, aplicar a lógica, os efeitos sonoros e mostrar o jogo. Essa sequência é feita através do game loop. Em um pseudo código, essa ação seria executada: Enquanto o jogo estiver rolando o laço será executado e as funções também: Serão chamadas. Em ler_entrada() são executadas as ações de leitura dos dispositivos de entrada, como:teclado, mouse. Já em atualizar_jogo() a lógica do jogo é aplicada em conjunto com os dados lidos dos dispositivos de entrada. Normalmente é nessa função que se verifica se o usuário perdeu ou ganhou o jogo e onde a variável jogo_rodando é atualizada, senão o jogo ficaria executando infinitamente. E em desenhar_jogo(), o jogo é redesenhado de acordo com as novas informações de atualizar_jogo(). Melhorando a jogabilidade Jogabilidade é termo utilizado para indicar a interação que o jogador tem com o jogo e que descreve a facilidade na qual o jogo pode ser jogado. Além de exibir as imagens na maior velocidade possível, um jogo precisa também dar resposta aos comandos do jogador. Para passar a sensação de tempo real, o jogo precisa atualizar a tela o mais rápido possível e processar os comandos do jogador no mesmo ritmo. Para realizar estas tarefas ao mesmo tempo vamos criar um loop principal que é simplesmente um loop onde os eventos de teclado e/ou mouse são capturados e revertidos em uma ação em um menor tempo possível. Iremos então melhorar a jogabilidade tornando o jogo mais divertido ao jogador criando um game loop. Vamos criar um novo arquivo javascript com o nome depong2.js que irá melhorar consideravelmente a jogabilidade, e resolver este problema de teclas pressionadas. Abra o Notepad e crie um arquivo em branco. Salve este arquivo com o nome de pong2.jsdentro da sua pasta no diretório js. Abra o arquivo pong.html e substitua o arquivo pong.js por pong2.js. Inicialmente vamos criar novamente a variável TECLA com os códigos de captura de teclas. Agora, vamos precisar de uma nova variável que irá armazenar a tecla pressionada pelos jogadores. Vamos chamar esta variável de jogo. Digite o código abaixo: Agora vamos ao código do game loop. Função setInterval A função setInterval() é nativa do JavaScript e é utilizada para indicar a unidade de tempo que um determinado evento irá acontecer. Neste jogo iremos criar uma variável que irá chamar uma função com o nome de loop a cada 30 milissegundos. Desta forma, teremos um temporizador que irá movimentar os batedores quando as teclas forem pressionadas. Funcionando no nosso caso, como o Game Loop clássico. Observe que a variável jogo.pressionou somente será verdadeira (true) quando a tecla for pressionada (keydown), e quando a tecla não estiver mais sendo pressionada (keyup) o valor da variável jogo.pressionou será falso (false). Agora vamos criar a função loop() que deixará o jogo em loop. A resposta ao teclado pressionado será executada pela função moveBatedores(). Também à criaremos. Observe que a lógica foi alterada. Antes, implementávamos as ações executadas pela função moveBatedores() dentro do eventokeydown(). Agora, nos eventos keydown() e keyup()apenas capturamos as teclas que estão sendo pressionadas e as atualizamos no array jogo.pressionou. A função loop() é executada a cada 30 milissegundos: E ela executa o método moveBatedores(): E este método verifica a tecla pressionada (a partir doarray jogo.pressionou) no momento e decide se vai reposicionar o paddle1 ou paddle2. Em resumo: Neste momento, o jogo faz a mesma coisa que fazia antes, mas com uma alteração de metodologia. Agora usamos o gameloop. Movimentando o asteroide dentro do game loop Iremos utilizar o mesmo temporizador criado para movimentar os batedores (o game loop) para movimentar o asteroide a cada 30 milissegundos. Inicialmente iremos criar uma variável que irá conter os valores da velocidade, posições x e y do asteroide e a direção atual da sua movimentação no eixo x e no eixo Y. O próximo passo é criar a funçãomoveAsteroide(). Inicialmente nesta função iremos criar variáveis que irão identificar a largura e a altura total da div fundo e, criaremos também, uma variável como nome de asteroide que terá o conteúdo da variável jogo.asteroide. Crie-a depois da função moveBatedores(): Para criar a movimentação da div asteroide somamos ao eixo x da variável asteroide o valor da variável asteroide.velocidade *asteroide.direcaoX. Efetuando este mesmo processo ao eixo y. Lembre-se que esse procedimento será executado a cada 30 milissegundos criando a movimentação da div no eixo x e no eixo y. Neste primeiro momento, as variáveis FundoAltura e FundoLargura não serão utilizadas. Mas depois elas serão. Vamos agora testar o funcionamento do código. Pressione [CTRL+S] para salvar as alterações e execute o arquivo pong.html. Observe que a div asteroide irá se movimentar no eixo x e no eixo y. Pressione a tecla F5 para reiniciar o efeito. Observe que a movimentação ainda não respeita os limites do jogo (a div #fundo). Antes de criar os limites do jogo vamos rever como é possível identificar possíveis erros no código do jogo. Visualizando possíveis erros no código Ao desenvolver um jogo ou qualquer aplicativo, durante o seu desenvolvimento podem ocorrer erros no código. Para visualizar estes erros, caso o jogo não apresente o resultado esperado. Para emular um erros, altere temporariamente o nome da função moveAsteroide() para moveAsteroideTESTE(). Isso vai gerar erro. Agora, clique com o botão direito do mouse sobre qualquer local da página no Chrome e selecione a opção Inspecionar elemento: Abrirá uma área na parte inferior do navegador, clique na aba Console e veja um descritivo de que existe um erro: O erro é específico. Cadê a função moveAsteroide()? Ela não existe, nós a renomeamos para moveAsteroideTESTE(). E em seguida, clique sobre o script pong2.js. Ele será aberto e nos será informado o local do erro: Usar o console durante o desenvolvimento é sempre importante, para evitar que algum erro passe em branco. Refaça a alteração, altere a função moveAsteroideTESTE() para o seu nome correto: moveAsteroide(). Salve as alterações. Agora vamos voltar para o jogo. Criando os limites de movimentação do asteroide Agora, vamos limitar a movimentação do asteroide dentro da div fundo. Iremos mudar a direção do asteroide caso ele chegue nos limites horizontais e verticais do fundo do jogo. Na função moveAsteroide() após a linha: asteroide.y += asteroide.velocidade * asteroide.direcaoY; Observe que caso o valor de y da variável asteroide seja maior que o valor da variável FundoAltura, será alterado o valor da variável asteroide.direcaoY para -1. Pressione [CTRL+S] para salvar as alterações e execute o arquivo pong.html. Observe que a div asteroide ao da div fundo irá mudar de direção. chegar no limite vertical Vamos agora limitar a movimentação da div asteroide quando a mesma chegar ao final da div fundo do lado direito. Observe que, identificamos que caso o valor da propriedade x da variável asteroide seja maior que o valor da largura da div fundo, o valor da variável asteroide.direcaoX será alterado para -1. Salve as alterações e execute o arquivopong.html. Observe que a div asteroide ao chegar no limite horizontal da div fundo mudará a sua direção. Vamos agora criar os demais limites de movimentação. Criando os demais limites de movimentação Criando os demais limites de movimentação. Salve as alterações e execute o arquivopong.html. Observe que agora a movimentação da div asteroide ficou limitada ao tamanho da div fundo. No próximo tópico iremos identificar as colisões com os batedores dos jogadores. Detectando colisões A detecção de colisões em jogos nada mais é do que identificar a intersecção de dois objetos diferentes. A detecção de colisões é uma das funções mais importantes no desenvolvimento de jogos, as funções de detecção de colisões são utilizadas para identificar a colisão e chamar uma resposta a esta colisão. Para identificar a colisão utilizaremos valores do eixo Xe Y do primeiro objeto e iremos comparar com os valores X e Y do segundo objeto. Caso esses valores sejam iguais (ou próximos em alguns casos) a detecção da colisão é realizada. Neste jogo em desenvolvimento iremos identificar a colisão da div #paddle1 (controlada pelo jogador 1) e da div #paddle2 (controlada pelo jogador 2) com a div#asteroide. Inicialmente vamos criar a detecção da colisão do batedor do jogador 1 (div #paddle1) com o asteroide(div #asteroide). Para isso vamos verificar se a div#paddle1 está sobreposta a div #asteroide mudando assim a sua direção. Criaremos uma variável com o nome de paddle1X que irá conter a posição left da divpaddle1 (valor obtido pela propriedade left) mais a largura da div paddle1 (valor obtido pela propriedade width): Desta forma será possível identificar o valor de x do batedor do jogador 1: Criaremos outra variável com o nome depaddle1YBaixo que irá conter o valor da propriedade top da div #paddle1 mais a altura da div paddle1 (valor obtido pela propriedade height). Desta forma será possível identificar o valor de y da parte inferior do batedor do jogador 1: Criaremos também, outra variável com o nome de paddle1YTopo que irá conter somente o valor da propriedade top da div #paddle1. Desta forma será possível identificar o valor de y na parte superior do batedor: Com esses valores é possível identificar se o valor de xe de y da div asteroide é o mesmo das áreas indicadas no batedor do jogador 1. Decretando colisão com o jogador 1 Vamos entender o código que foi criado para identificar a colisão. Observe que inicialmente foram criadas as variáveis indicadas no inicio desta unidade: Depois é verificado se o valor da propriedade de x da variável asteroide é menor que o valor da variável paddle1X. Isso indicará que a div asteroide está posicionada no mesmo local do paddle1. Caso essa condição seja verdadeira será verificado se o valor de y da div asteroide é menor ou igual a variável paddle1YBaixo e é maior ou igual a variável paddle1YTopo. Isso irá verificar se o valor de y da div asteroide está entre a altura da div paddle1confirmando a colisão. Caso esse condição for verdadeira será alterado o valor da variável asteroide.direcaoX para 1. Agora, vamos fazer uma pequena refatoração. Observe que na parte que detectamos a colisão, selecionamos o elemento #paddle1: E na função moveBatedores() também o selecionamos: Se essas variáveis paddle1 e paddle2 são utilizadas globalmente no arquivo, em mais de uma função, por que não a tiramos do escopo local da função moveBatedores() e colocamos no escopo global, antes das funções? Assim, selecionamos esses elementos apenas uma vez no início da execução e ganhamos em performance. Façamos isso, remova função moveBatedores(): essas variáveis da Remova também a referência da variávelpaddle1 na parte de detecção de colisão: Agora, no escorpo global do variáveis paddle1 epaddle2. do array jogo.asteroideacrescente: arquivo, inicializaremos as Logo abaixo Por enquanto elas foram apenas inicializadas. Vamos armazenar nelas as referências dos elementos apenas quando a página for carregada. E isso é feito lá em baixo, dentro da função especial do jQuery que indica que a página foi devidamente carregada: O código ficou melhor. Agora vamos partir para a detecção de colisão com o jogador 2. Detectando colisão com o jogador 2 Observe que neste código a variável paddle2Xfoi subtraído o valor 51 unidades: Utilizamos esse valor para que seja subtraída a largura da div asteroide, para que a colisão seja detectada no local correto. Salve as alterações e execute o arquivopong.html. Observe que agora a colisão com a div paddle2 é identificada. Textos dinâmicos Nesta unidade iremos criar textos dinâmicos para exibir a pontuação dos jogadores. Os jogadores irão pontuar sempre que a div asteroide ultrapassar a div do jogador (paddle1 oupaddle2). No exemplo abaixo o jogador 1 irá pontuar: Inicialmente iremos criar uma nova div no arquivo pong.html após a div fundo com o nome de pontuacao. Vamos agora editar o arquivo pong2.js. Inicialmente vamos criar uma variável com o nome de pontuacao que irá receber os pontos do jogador1 e dojogador2. O jogador 1 irá pontuar quando o propriedade x da div asteroide for maior que a largura do fundo do jogo. Salve as alterações no código e execute o arquivo pong.html. Observe que a pontuação será exibida: Vamos agora, exibir a pontuação do jogador 2. Exibindo a pontuação do segundo jogador O jogador 2 irá x da div asteroide for jogo (menor que 0). pontuar quando o propriedade menor que a largura do fundo do Altere o if: Salve as alterações no código e execute o arquivo pong.html. Observe que a pontuação dos dois jogadores serão exibidas. Elemento áudio Nesta unidade iremos utilizar o elemento audio do HTML5 para executar sons no jogo. Utilizando-o juntamente com recursos do JavaScript para referenciar e executar arquivos de áudio, vamos inserir uma música de fundo para o jogo e executar sons quando o asteroide entrar em colisão com os batedores do jogador1 e do jogador2. Uma observação importante quando for utilizar arquivos de áudio é que os diferentes tipos de navegadores não executam todos os formatos de áudio, utilize sempre arquivos no formato MP3 ou OGG, que são executados sem problemas nos navegadores Chrome, Firefox e Safari. O elemento < audio > possui alguns atributos que devem ser observados. Veja o exemplo abaixo: Autoplay: a propriedade autoplay indica que arquivomusica.mp3 deve ser executado automaticamente. o Controls: Se este atributo controls estiver presente, o navegador oferecerá controles para permitir que o usuário controle a reprodução do áudio, incluindo volume, procura e pausar/continuar. Loop : Faz com que o áudio repita automaticamente. Preload: O atributo preload é usado em elementos áudio para carregar arquivos grandes. Caso o valor deste atributo seja verdadeiro, o arquivo de som será pré-carregado antes de sua execução evitando possíveis atrasos em sua execução. Vamos inicialmente indicar pelo elemento < audio > os arquivos que serão executados pelo código JavaScript. Caso você execute o arquivo, você irá observar que os arquivos de sons não serão executados, pois, não utilizamos a propriedade autoplay. Iremos indicar a execução desses arquivos através do arquivo JavaScript. Abra o arquivo pong2.js. Inicialmente vamos criar uma variável para controlar a execução do som. Agora vamos executar esse som, sempre que os batedores dos jogadores 1 e 2 entrarem em colisão com o asteroide, na função moveAsteroide(). Na área onde existem os if’s que verificam colisões, acrescente: Salve as alterações. Execute o arquivopong.html e verifique o resultado. Observe que agora o som e executado toda vez que o asteroide entrar em colisão com os batedores dos jogadores 1 e 2. Uma música ficou em looping (em repetição) no "fundo". Isso, graças ao atributo "loop" do elemento "audio": Criando uma condição de fim de jogo Nesta unidade iremos criar uma condição que irá indicar quando o jogo será finalizado. Iremos finalizar o jogo quando o primeiro jogador atingir 5 pontos. Para isso devemos sempre verificar a variável de pontuação de cada jogador e quando atingir 5 pontos iremos executar uma função chamada de GameOver( ) que irá pausar a música, exibir uma mensagem de fim de jogo e reiniciar o jogo. Abra o arquivo pong2.js. Digite o código que executará gameOver( ) abaixo da funçãomoveAsteroid( ) após a pontuação dojogador2, antes do comentário: Detectando as colisões. O código acima nos diz que, quando ojogador1 ou jogador2 tiver 5 pontos, a função gameOve( ) é executada. Agora vamos criar a função gameOver( ). Essa função irá pausar a música de fundo, irá indicar quem ganhou o jogo e irá reiniciar o jogo quando o botão OK for pressionado. Digite o código para criar a função GameOver( ): Salve as alterações. Execute o jogo e veja o resultado quando algum jogador tiver conseguido 5 pontos. Armazenamento Local Iremos utilizar os recursos de armazenamento local do HTML5 para exibir o último placar do jogo mesmo que a página do site seja atualizada ou fechada. Desta forma quando o jogo for reiniciado serão exibidos para o jogador o último placar. Iremos também exibir a data e hora da última partida realizada. Os dados armazenados utilizando esse recurso são armazenados em forma de cookies e podem ser armazenados até 4 GB de informação. Lembrando que as informações armazenadas no browser Google Chrome, por exemplo, não estarão disponíveis em outro browser como o Mozilla Firefox. Para utilizar este recurso iremos utilizar o comando localStore, utilizando a propriedade localStore.setItem para indicar o item que será armazenado e a propriedade localStorage.getIt em para obter o item salvo. Inicialmente vamos criar as divs onde os dados serão exibidos ao jogador. Digite o código no arquivo pong.html após o fechamento da div pontuação pela tag < /div > Salve as alterações no arquivo. Agora na função GameOver() vamos utilizar o comando localStore para armazenar os dados obtidos pela partida realizada. Altere a função gameOver() e também acrescente acima dela a função infoGame(). Agora, na função, acrescente. Ou seja, mesmo que o usuário feche o navegador, ao abri-lo posteriormente, os dados do último jogo serão escritos na tela. Canvas Inicialmente produzido pela Apple para o navegador Safari, o elemento < canvas > é utilizado para delimitar uma área do browser onde a mesma irá receber imagens, ou renderização de gráficos como: linhas, círculos, retângulos, etc., que podem ser criados através de script. Nesta unidade iremos conhecer os principais recursos deste elemento. Abra o Notepad e crie um documento em branco. Digite para ele a estrutura básica de um código HTML. “canvas1.html” Observe que no código acima definimos o elementos "canvas" pela tag < canvas > com o nome de "meuCanvas" definindo o seu tamanho em 600px de largura por 400px de altura. Após definir o elemento canvas, dentro do código JavaScript, é possível desenhar retângulos, caminhos (Paths) que incluam segmentos de linhas e arcos, posicionar arquivos de imagem sobre canvas, etc. É possível também criar preenchimentos dentro de retângulos e caminhos. Para desenhar um objeto sobre o canvas é necessário indicar as coordenadas do seu posicionamento. Na figura abaixo mostra o layout de um objeto canvas no tamanho de 600px por 400px, os números indicam as coordenadas de cantos e do meio do objeto canvas: Elemento Canvas Vamos agora criar um código JavaScript que criará os elementos necessários para a criação de objetos no canvas. Dentro da tag < script > no < head > do documento, acrescente o código JavaScript. Observe que foram criadas duas variáveis, uma com o nome de canvas e outra com o nome decontext. A variável canvas será utilizada para indicar a área do canvas no browser. Observe que indicamos no código HTML o tamanho de 600 pixels de largura por 400 pixels de altura: Na variável context indicamos que serão utilizados recursos de renderização em 2 dimensões. Vamos agora desenhar uma linha. Desenhando uma linha Altere o código JavaScript dado anteriormente. Em execução no navegador: A linha abaixo: Define o ponto inicial da linha no canvas. A linha abaixo: Define o ponto final da linha no canvas. Esta linha, desenha a linha. Desenhando um retângulo Vamos substituir o código que criou a linha por um código que criará um retângulo. Em execução: A linha em seguida, inicia o caminho de renderização. A linha abaixo, cria um retângulo indicando a posição x, y inicial e valores para a largura (width) e para a altura do objeto (height). Desta fora este objeto terá a largura de 200 pixels e a altura de 100 pixels. A linha abaixo, define a cor de preenchimento. Em seguida esse preenchimento é renderizado: Indica a largura do contorno: A cor do contorno: Renderiza o contorno: Criando um círculo Para desenhar um círculo com HTML5 Canvas, podemos criar um arco usando o método arc()e definir o ângulo inicial como 0 e ângulo final com a fórmula matemática 2 * PI. Substitua o código utilizado para criar o retângulo. Em execução: Operações com imagens e textos usando Canvas Crie um novo arquivo. Digite a estrutura código HTML com o elemento canvas. básica de um Salve o arquivo com o nome de canvas2.html. Exibindo imagens no canvas Primeiro copie a pasta canvas do arquivos-cursos\html5 para sua pasta e coloque o arquivo canvas2.html na mesma pasta. Para exibir uma imagem usando HTML5Canvas, é utilizado o método drawImage()que requer um objeto de imagem e um ponto de destino identificado pelas coordenadas x e y. Altere o script do arquivo. Em execução: Trabalhando com textos Vamos agora criar um texto que irá aparecer após a imagem ser renderizada. Vamos utilizar o método fillText dentro da função imagem.onload: Em execução: Onde primeiro, indicamos o estilo da fonte o tamanho e tipo da fonte. A cor da fonte: E por último definimos o texto e sua posição. Criando uma animação utilizando uma imagem mapeada Com uma imagem mapeada, é relativamente simples criar uma animação baseada em células. Esta técnica envolve a troca rápida das imagens para simular uma animação. Para utilizar uma imagem mapeada, antes é necessário criá-la, no exemplo abaixo a imagem foi criada utilizando o Adobe Photoshop, utilizando como tamanho de cada célula 32 pixels de largura por 32 pixels de altura: Totalizando 8 células de largura por 3 células de altura Desta forma podemos identificar cada um dos quadrantes da imagem (células) da seguinte forma: Crie um documento em branco no Notepad. Digite a estrutura básica de um código HTML. (canvas3.html) Crie também um arquivo chamado canvas3.js, que é onde colocaremos os scripts do exemplo. Vamos agora executar uma função assim que a janela do browser for carregada. Agora vamos criar a função canvasApl(). Observe que no código acima criamos os elementos principais do canvas e carregamos imagem tanks.png. Agora vamos indicar quais quadrantes (células) da imagem mapeada serão utilizados na animação. Digite o código no início do arquivo. Observe que criamos uma variável do tipo Array que irá receber a posição das imagens que serão utilizados na animação. Observe que foi criada também uma variável com o nome de frameIndex que contém o valor de controle do índice da Array. Vamos criar mais 3 variáveis que irão possuir o valor do ângulo de rotação da animação do tank e de seu posicionamento no canvas. Digite o código no início do arquivo. (canvas.js) Agora vamos criar uma função com o nome de desenhaTela() que irá renderizar o canvas e exibir a animação. Digite o código. Para finalizar, acrescente estas funções no arquivo. Execute o exemplo: Criando uma animação utilizando uma imagem mapeada Observe que foi indicado a cor do fundo do canvas: O seu posicionamento: E utilizamos a propriedade setTransform: Para redefinir a matriz de transformaçãoHTML5 Canvas para seu estado padrão, utilizando os valores 1,0,0,1,0,0. Deve-se redefinir a matriz de transformação sempre que o canvas estiver dentro de um loop. Como o objeto será girado dentro do canvas, alteramos o seu ponto de referência da matriz para o centro da imagem: Como o quadrante da imagem mapeada possui o tamanho de 32 pixels, movemos o ponto central na metade desse valor:16 pixels. Em seguida indicamos quais quadrantes serão exibidos na animação: Estamos usando o frameIndex da matriz animationFrames para calcular a célula da imagem mapeada que será exibida na tela. Primeiro, é necessário encontrar o valor de x e de y do canto superior esquerdo de cada quadrante. Para encontrar o valor de x criamos uma variável como nome de sourceX que irá conter o valor do(frameIndex % número de colunas da imagem) * largura da imagem. O operador módulo (%) retorna o resto de uma divisão, por exemplo, o primeiro quadrante está posicionada no valor 0 da variável frameIndex sendo assim o cálculo ficará: 0 % 8 onde o resultado é 0, multiplicado por 32se terá o resultado 0 indicando o valor de x do primeiro quadrante. No segundo quadrante o valor do frameIndex será 1, sendo assim o cálculo será 1 % 8 onde o resultado será1, multiplicado pode 32 se terá o resultado 32 indicado o valor de x do segundo quadrante, e assim por diante. Para encontrar o valor da posição do eixo y dividimos o valor do frameIndex por 8 e multiplicar pelo tamanho do quadrante. Agora usamos o método drawImage(): Para exibir cada uma das células no canvas. Iremos também atualizar o valor do frameIndex: Assim exibindo cada um dos quadrantes da animação. Criando um level com imagens mapeadas Nesta unidade vamos criar um fundo do jogo utilizando os conceitos aprendidos na unidade anterior. Criaremos uma imagem de fundo do jogo utilizando os conceitos de imagem mapeada. Iremos utilizar os quadrantes 0, 20 e 21 para definir a imagem de fundo. O fundo do jogo será formado por 10 quadrantes de 32px na sua largura e 10 quadrantes de 32px na sua altura. Iremos indicar os quadrantes da seguinte forma: Obtendo o seguinte resultado: Abra o Notepad++ e crie um arquivo chamadocanvas4.html. Agora, crie o arquivo canvas4.js, executar uma função assim que a janela do browser for carregada. Agora vamos criar a função canvasApl(). Digite o código. Vamos agora criar algumas variáveis. Digite o código. As variáveis abaixo, indicarão o total de quadrantes para a largura e para a altura. Já a variável Mapa, irá conter as coordenadas dos quadrantes que serão utilizados: Observe que utilizamos os mesmos recursos aprendidos no capítulo anterior para preencher o canvas com os quadrantes da imagemtanks.png. Canvas Game Nesta unidade daremos início ao desenvolvimento de um novo jogo. Criaremos o jogo com base no documento de jogo abaixo. Nome do jogo: Tank! Tema: Jogo para 1 jogador onde o jogador irá controlar um tanque tendo como objetivo recolher um número maior de bandeiras do que o tanque controlado pelo computador. Esse jogo poderá ser jogado on-line via browser e também em dispositivos móveis Android em forma de aplicativo. Tanto a versão on-line quanto a versão em forma de aplicativo terá o seguinte layout: Controles: Para dificultar o jogo, o jogador apenas poderá girar o tanque em sentido horário. A cada clique ou toque na área do jogo o tanque irá girar 45° em sentido horário. Fim de jogo: O jogo será finalizado quando o jogador ou o computador recolher o número de 10 bandeiras. Iremos dar início ao desenvolvimento deste jogo pelo seu layout. Criando Layout do jogo Crie uma pasta como o nome de Tank dentro de sua pasta e descompacte o arquivotank.zip em seu interior. Esse arquivo encontra-se em /arquivos-cursos/html5. Observe que uma série de pastas serão criadas: Crie um novo arquivo HTML no Notepad. Salve este arquivo com o nome de index.htmldentro da pasta tank. Agora, crie um novo arquivo vazio e salve-o dentro da pasta css com o nome de:estilos.css. Vamos iniciar o código CSS do jogo indicando o arquivo de fonte que será utilizado no título do jogo. Iremos utilizar o arquivo BRAESIDE.ttf salvo na pasta fonte. Vamos agora indicar a imagem que será utilizada como fundo. Digite o código no arquivo CSS. Para finalizar o código CSS vamos indicar a formatação para a div #fundo. Salve as alterações no arquivo. Execute o arquivo index.html. Veja que a estrutura do jogo foi criada: Criando o mapa do jogo Neste tópico criaremos o arquivo tank.js e inicialmente iremos construir o mapa do jogo utilizando uma imagem mapeada. Crie um novo arquivo. Salve este arquivo com o nome de tank.js na pasta js. Agora iremos criar um evento que será executado quando a janela do browser for carregada. Na função canvasApl criaremos o canvas dentro da div #fundo, além de criar e atribuir os valores inicias para o desenho do mapa. Mapas mais complexos Para a criação de mapas mais complexos você pode utilizar alguns programas que facilitam a construção de levels utilizando imagens mapeadas. Como o http://www.mapeditor.org/, http://tilestudio.sourceforge.net/. ou o No exemplo do curso, utilizamos o Tile Studio. Caso não consiga baixá-lo pelo site oficial, na pasta /arquivoscursos/html5, temos ele zipado com o nome de ts.zip. Após criar o mapa, pode-se obter uma série de tipos de arquivo onde e possível utilizar o mapa gerado: Carregando os objetos Agora vamos criar função gameLoop(). Agora vamos criar o mapa no canvas. a função iniciar(), a que irá função desenhaTela que chamar irá a exibir Salvar as alterações no arquivo tank.js. Execute o arquivo index.html e visualize o resultado. Observe que o mapa foi gerado na div#fundo: Desenhando o primeiro Tanque Vamos agora criar o código que irá exibir o tanque que será controlado pelo jogador no canvas. Inicialmente vamos criar as variáveis que serão utilizadas pelo tanque1. No inicio do arquivo tank.js: Observe que foram criadas duas variáveis com valores randômicos entre 0 e 400. Essas duas variáveis serão utilizadas para o posicionamento aleatório do tanque1 no mapa. Vamos agora criar a função desenhaTank1(). A função desenhaTank deve do GameLoop do jogo. Desta método gameLoop(): ser forma, executada dentro chame-a dentro do Salve as alterações no arquivo tank.js. Execute o arquivo index.html e veja o resultado. Observe que cada vez que a página é atualizada o tanque1 será exibido em um local aleatório do mapa. Criando a movimentação do Tanque1 A direção da movimentação do tanque1 será definida pelo jogador através do clique no mapa. Desta forma vamos criar um evento que irá identificar o clique na área do mapa do jogo. O que será executado na função eventoClick()? Criaremos uma variável com o nome de direcao, que irá conter o valor inicial de 1. Toda vez que a área do mapa for clicada, será somado uma unidade a esta variável, até ela receber o valor máximo 4. Quando o mapa for clicado pela quinta vez o seu valor será reiniciado para 1. Desta maneira esta variável irá conter a direção que o tanque1 deverá se movimentar. Vamos incialmente criar a funçãoeventoClick(). Agora vamos criar a variável direcao. Digite-a no começo do arquivo. Agora para movimentar o tanque1, vamos criar a função atualizarTanque1, onde criaremos o código que irá movimentar o tanque1 de acordo com o valor da variável direcao. Além de indicar a direção que o tanque1 deverá se movimentar, também devemos girar a imagem de acordo com a direção da movimentação. Salve o arquivo, execute o arquivo index.html e veja o resultado. Observe que quando o jogador clicar na área do mapa a movimentação do tanque será alterada em sentido horário. Limitando a movimentação do Tanque1 Vamos agora limitar a movimentação dotanque1 dentro da área do canvas, evitando que o tanque saia da área de visualização do jogador. Iremos realizar esta operação alterando o valor da variável movimentação da seguinte forma: Desta forma, modifique o código da funçãoatualizarTanque1(). Salve as alterações no arquivo tank.js. Execute a aplicação e observe que caso o tanque chegue nos limites do canvas a sua movimentação será alterada automaticamente: Desenhando o Tanque2 (inimigo) Para desenhar o tanque2 que será controlado pelo computador vamos iniciar criando as variáveis necessárias. Dentro do método canvasApl, digite o código . Vamos agora criar a função que irá desenhar o tanque inimigo. Digite o código para criar uma função com o nome de desenhaInimigo(). Agora vamos executar essa função dentro do GameLoop do jogo. Salve as alterações no arquivo tank.js. Execute o arquivo index.html e veja o resultado. Observe que o tanque inimigo será exibido em um local aleatório toda vez que a página for atualizada. Agora vamos criar a função que irá exibir abandeira em uma posição aleatória no mapa. Desenhando a bandeira Inicialmente vamos criar as variáveis necessárias para a criação da bandeira. Dentro do método canvasApl, digite o código. Vamos agora criar uma função com o nome desenhaBandeira() que irá exibir a bandeira no canvas. de Digite o código para criar a função. Agora vamos executar essa função dentro do Game Loop do jogo. Salve as alterações no arquivo tank.js. Execute o arquivo index.html e veja o resultado. Observe que a bandeira será exibida em um local aleatório toda vez que a página for atualizada. Inteligência Artificial Inteligência Artificial, ou simplesmente IA, é o que controla e orienta oponentes computadorizados para proporcionar desafios ao jogador. Nesta unidade iremos criar a inteligência artificial que irá controlar o tanque inimigo. Será uma IA rudimentar que apenas irá fazer com que o tanque inimigo chegue de uma forma que seja o mais rápido possível onde está a bandeira. Iremos criar esse comportamento fazendo um comparativo dos valores de x e y do tanque2 com os valores de x e y da bandeira, fazendo com que otanque2 se movimente até o local da bandeira. Para isso, vamos criar o método atualizarInimigo(). Observe que caso o valor da posição x dotanque2 for maior que a posição x da bandeira, o valor de x do tanque2 será subtraído, fazendo com que o tanque2 fique na mesma posição x da bandeira. Caso o valor de y do tanque2 for menor que o valor de y da bandeira, o valor de y dotanque2 será somado, fazendo que fique na mesma posição y da bandeira, e assim por diante. Vamos chamar essa função no game loop. Salve as alterações no arquivo tank.js. Execute o arquivo index.html e veja o resultado. Observe que o tanque inimigo irá se movimentar automaticamente até a posição da bandeira: Detectando colisões da bandeira com o tanque inimigo Neste tópico vamos detectar a colisão do tanque inimigo com a bandeira, fazendo com que a bandeira seja reposicionada em um novo local. Para isso, vamos criar um chamado detectandoColisaoBandeira(). novo método Como o tanque2 é movimentado 1 unidade cada vez dentro do eixo x e do eixo y, podemos comparar se o valor de x e y dele é o mesmo valor de x e y da bandeira, detectando assim a colisão. Agora vamos chamar esse método dentro do game loop. Salve as alterações no arquivo tank.js. Execute o arquivo index.html e veja o resultado. Observe que a bandeira será exibida em uma nova posição quando o tanque inimigo entrar em colisão com ela. Detectando colisões da bandeira com o tanque 1 Para o tanque1, não podemos utilizar o mesmo sistema de colisão que usamos com o tanque inimigo, pois o tanque1 não se movimenta 1 unidade cada vez nos eixos x e y e sim 2unidades, desta forma os valores de x e y do tanque1nunca serão iguais aos valores x e y da bandeira. Para detectar a colisão iremos fazer um comparativo de x e y do tanque1 somados a sua largura e altura (32 pixels) com os valores de x e y da bandeira. Para que a área de colisão seja mais próxima da imagem da bandeira iremos somar apenas 16 unidades na comparação ao invés de 32 unidades. Desta forma, o nosso método de colisão será modificado. Salve as alterações no arquivo tank.js. Execute o arquivo index.html e veja o resultado. Observe que a bandeira será exibida em uma nova posição quando otanque1 entrar em colisão com ela. Pontuação e comportamento de fim de jogo Para exibir a pontuação no canvas vamos criar uma nova função com o nome de desenhaTexto(): Vamos criar as variáveis pontosjog e pontoscomp: Agora vamos somar a variável pontosjog toda vez que o tanque1 entrar em colisão com abandeira e somar a variável pontoscomp toda vez que o tanque inimigo entrar em colisão com a bandeira. Desta forma, vamos modificar o método dectandoColisaoBandeira(). V amos agora criar uma função com o nome de gameOver() que irá detectar o fim do jogo. Quando o jogador1 ou o computador atingir10 pontos será o vencedor. Digite os comandos para criar a função gameOver(): Insira agora a função gameOver e do game loop do jogo. a desenhaTexto dentro Salve as alterações no arquivo tank.js. Execute o arquivo index.html e veja o resultado. Que uma mensagem será exibida quando o primeiro jogador atingir 10 pontos, em seguida, o jogo será reiniciado. Executando sons Inicialmente vamos indicar < audio > os arquivos que código JavaScript. Desta forma, arquivo index.html logo < body >: pelo elemento serão executados pelo digite o código no após a tag No arquivo tank.js inicialmente vamos as variáveis que irão manipular os sons: E dentro do método canvasApl, vamos vinculá-las aos elementos da página. No caso, da variável som, ela executará o som, sempre que houver uma colisão com abandeira, por isso, vamos modificar o método de colisão e dentro dos ifs executar o som. E para a música de fundo, vamos parar a sua execução, quando um jogador ganhar o jogo. Portanto, altere a função gameOver(). Salve as alterações. Execute o arquivo index.html e verifique o resultado. Observe que agora um som de fundo é executado, e toda vez que uma colisão com a bandeira é encontrada, outro som também é executado. Convertendo o jogo em um aplicativo para dispositivo móvel Este jogo caso ele esteja hospedado em um servidor na internet ele pode ser executado em qualquer dispositivo móvel (desde que tenha resolução suficiente para exibir o jogo) via browser. Outra possibilidade é criar um aplicativo que será instalado no dispositivo móvel e o jogo poderá ser executado independentemente de uma conexão com a internet. Nesta unidade vamos gerar um aplicativo móvel utilizando o PhoneGap. O PhoneGap é um framework de desenvolvimento móvel produzido pela empresa Nitobi, comprada recentemente Adobe Systems. O PhoneGap converte em aplicativos nativo para iPad (iOS), Android,Windows 8 entre outros, arquivos criados em JavaScript, HTML5 e CSS3. Desta forma um mesmo projeto pode ser distribuído para diversos sistemas operacionais utilizando apenas uma fonte de código. Antes de convertermos o jogo em aplicativo móvel, devemos criar um arquivo XML que terá todas as informações sobre o aplicativo, como versão, ícone a ser utilizado, propriedade do aplicativo, etc. Inicie o NotePad e crie um novo arquivo. Salve este arquivo na pasta tank com o nome de config.xml. Observe que foram indicados o nome do aplicativo pela tag < name >, o caminho do ícone que será utilizado pelo aplicativo pela tag < icon > entre outras especificações. Entre elas a execução do aplicativo em tela cheia indicada pela linha de comando: Pressione [CTRL+S] para salvar o arquivo. Vamos agora compactar todos os arquivos utilizados no jogo em um arquivo do ZIP (não utilize o formato RAR) para que seja gerado o aplicativo pelo PhoneGap. Selecione todos os arquivos da pasta tank e os compacte em um arquivo com o nome detank.zip como indicado na imagem abaixo: Vamos agora utilizar http://www.phonegap.com/. o PhoneGap. Desça a barra de rolagem e clique em "Try Now": No link Para utilizar o PhoneGap é necessário uma conta na Adobe chamada de Adobe ID ou se registrar no Gtihub. Neste exemplo iremos utilizar o Adobe ID. Clique no botão ...with Adobe ID: Caso você não tenha um registro da Adobe, dê um clique no botão Create an Adobe ID: Observe que um formulário de registro será exibido. Preencha este formulário com os seus dados e clique no botão Create. Para ter acesso a versão em Português deste formulário acesse o link:https://www.adobe.com/cfusion/member ship/index.cfm?loc=pt_br&nl=1. Abra o PhoneGAp utilizando o Adobe ID. Observe que a seguinte tela será exibida: Dê um clique no botão Upload a .zip file. Selecione o arquivo tank.zip criado anteriormente. Observe que as informações indicadas no arquivo config.xml serão exibidas: Dê um clique o botão Ready to build: Aguarde os aplicativos serem gerados. Para desenvolver aplicativos para iOS (iPad, iPhone etc.) é necessário possuir um número de certificação de desenvolvedor fornecido pela Apple, por isso neste exemplo o aplicativo iOS não será gerado. Dê um clique sobre o ícone do sistema operacional Android: Observe que o arquivo .apk poderá ser baixado: É possível também baixar o aplicativo diretamente no dispositivo móvel utilizando QR Code gerado automaticamente pelo PhoneGap. Veja nas imagens abaixo o jogo instalado como aplicativo e sendo executado em um Table Nexus 7 (Android 4): Em execução no Tablet: