Elementos de interface consomem muito esforço na elaboração de um jogo, mas são imprescindíveis. Sendo assim, é interessante criar classes para cada tipo de elemento de interface que será necessário no projeto. É o caso da classe a seguir, que especifica um objeto de botão.
O construtor da classe espera uma imagem passada como referência e a adiciona juntamente com ouvintes necessário. No código abaixo, somente um ouvinte foi adicionando, mas em um botão é comum adicionar mudança no botão quando o mouse está sobre ele (que ficará como tarefa para praticar).
Observe que no evento de clique é verificado se o clique ocorreu em cima do botão instanciado e se sim, a codificação aciona o método stopPropagation() que encerrará a verificação do evento por parte do restante das outras instâncias, economizando recursos. Em seguida é criado um novo evento, chamado de “click” que poderá ser utilizado posteriormente para qualquer ouvinte de objeto instanciado dessa classe e representando essa ação.
Para praticar: faça com que o botão tenha 2 formas: a primeira é sua imagem normal, a segunda de quando o botão for pressionado. |
Gerenciamento de cenas
Um jogo pode ser visto como a composição de várias cenas, onde cada cena representa uma parte do jogo. Por exemplo, um jogo pode ter a tela inicial, o primeiro nível do jogo e o segundo nível do jogo, sendo esses exemplos podendo gerar uma cena para cada um.
O gerenciamento de cenas na Gideros é facilitado pelo script Scene Manager, disponível no endereço https://github.com/gideros/Scene-Manager. Veremos agora como utilizá-lo, sendo necessário inicialmente baixar o scritp scenemanager.lua e adiciona-lo ao projeto do jogo.
Consideraremos para o jogo a existência de 3 cenas: uma de início do jogo, uma com informações sobre o jogo e uma com o jogo propriamente dito. O código abaixo relaciona essas três cenas, instanciando-as utilizando o script do Scene Manager. Esse código adicionado ao arquivo main.lua adicionará o gerenciamento de cena no jogo e também fará a chamada da cena identificada como “inicio”, indo para essa cena. As cenas ainda não foram criadas, mas vemos que elas já possuem um rótulo e recebem o nome da classe que conterá a cena propriamente dita.
Como tela inicial iremos criar dois botões que conduzirão para o jogo ou para a tela de créditos. A tela será criada a partir do arquivo inicio.lua e os botões serão estabelecidos de uma forma diferente da vista até o momento e faz uso da “Gideros texture packer”, software instalado juntamente com a Gideros.
Para começar a utilizar a aplicação, acesse a opção “File” e depois “new project”. Será solicitado um nome de projeto e um diretório de armazenamento, onde recomendo escolher o mesmo local do projeto do jogo e desmarcar a opção “create directory for project” (a menos que você tenho muitos scripts e elementos gráficos no jogo). O nome que será utilizado no projeto ilustrado nesse material é “botoes”, já que utilizaremos esse texture packer para armazenar todos os botões do jogo.
Figura 3.1 – tela de projeto do Gideros texture packer
Tendo criado o projeto do texture packer, clique com o botão direito do mouse no nome do projeto na janela a esquerda (assim como fazemos para adicionar elementos na Gideros) e acesse a opção “add existing files”, selecionando os arquivos desejados. Se algum for esquecido, não tem problema e ele poderá ser adicionado posteriormente. Na área da direita é mostrado o arranjo gerado com as imagens adicionadas ao projeto. Não importa o arranjo já que o funcionamento será igual, indiferente de como ele tenha ficado, mas é esse arranjo que irá compor a imagem do texture packer.
Tendo definido as imagens necessárias, basta acessar o menu “file” e a opção “Export texture”, que salvará todas as imagens relacionadas em um único arquivo e este será adicionado a pasta do projeto juntamente com um arquivo txt com especificação dos elementos presentes na imagem (se você escolheu o loca do projeto da textura sendo o mesmo do projeto do jogo). Esses arquivos ainda precisarão ser incorporados ao projeto, mesmo já estando na pasta do projeto.
Vamos agora especificar esse script de início juntamente com as texturas geradas. O código a seguir mostra a criação da classe “Inicio” e os códigos do construtor. O construtor inicia instanciando o método TexturePack.new() que precisa receber o arquivo de texto com a configuração da textura e a textura propriamente dita. Em seguida criamos um bitmap baseado em uma região dessa textura, informando o nome da região, que é o mesmo nome da imagem que foi utilizada na criação da textura. Veja que com essa técnica duas coisas são facilitadas: 1) menos arquivos de imagem são necessárias no projeto; e 2) alterar qualquer arte dos botões exigirá apenas alterar o projeto do texture packer, sem contar que utilizar skins diferentes exige apenas a definição uma nova imagem com as texturas.
A seguir o código cria um novo botão (fazendo uso do script visto na sessão anterior), posiciona-lo e adiciona-o efetivamente na cena. Para finalizar o botão, é associado um evento de clique que ao acontecer, executará uma função que chamará a cena do jogo, cena onde pretendemos ter o jogo efetivamente.
Logo em seguida é criado outro botão que é posicionado logo abaixo do anterior e que ao ser clicado conduzirá para a cena que conterá informações do jogo.
Um detalhe importante é que os elementos gráficos estão sendo criados na própria classe e se for criado um elemento gráfico no stage, esse persistirá na tela independente da troca de cenas.
Na elaboração da cena com informações sobre o jogo, criamos uma nova classe e posicionamos nela uma área de texto e depois um novo botão, segundo visto na elaboração da tela inicial, e que conduzirá para a página de início ao ser clicado.
Nossa última cena conterá o jogo propriamente dito e esse iniciará com a codificação já vista anteriormente, onde termos uma bola que irá descendo na tela. Nesse jogo é esperado que o jogador clique na bola, contabilizando pontos e fazendo a bola voltar para o topo.
Nosso próximo passo consistirá em criar um botão que realizará um reinício no jogo, um botão de reload. Iniciaremos com o posicionamento do botão no canto inferior esquerdo da tela. Esse botão está presente na texture pack mostrada anteriormente. O código abaixo adiciona o botão e na última linha adiciona um evento no botão que, quando clicado, chama novamente a cena que estamos através do scenemanager. Isso basta para trazer os recursos de reiniciar para o jogo, fazendo a cena ser novamente chamada para a execução.
Além do botão de reinício, vamos adicionar um botão abrirá um menu que poderia oferecer opções de configuração do jogo ou simplesmente anunciar a pausa do jogo (o recurso de pausa é solicitado com exercício para praticar ao final dessa sessão). O código abaixo adiciona o botão de menu juntamente com o de reinício e o evento de clique dele chama a função openMenu() que será especificada a seguir.
A função openMenu() é responsável por verificar se o menu existe na tela. Inicialmente é estado se o objeto “menu“ já existe, se existir ele será apenas adicionado na tela, aparecendo efetivamente. Caso ele não exista, significa que é a primeira vez que o botão de menu é clicado, é criado um menu através da função createMenu(), definida a seguir.
A função createMenu() utiliza a criação de formas gráficas através de código. Poderia ser utilizada uma imagem, forma utilizada anteriormente, mas nesse caso foi optado pela criação assim. O código inicia com a instanciação de uma classe Shape e que é seguida da especificação de qual formato de linha será utilizado para contornar a forma, sendo configurado um formato sólido, na cor preta e uma espessura de 0.5. A seguir são especificados pontos que serão utilizados para traçar linhas e formar a forma pretendida são especificados 4 pontos através da passagem de suas coordenadas. O método closePath() completa a forma unindo o último ponto especificado ao primeiro e o método endPath() é quem especifica a finalização da especificação da forma.
Após criar a forma, são adicionados dois eventos vinculados ao MOUSE_DOWN e ao MOUSE_UP, onde eles realizarão a parada da propagação desses eventos, retirando os ouvintes existentes para esses dois eventos. Sendo assim, ao criar o menu esses eventos não mais funcionarão, então os outros elementos (no nosso caso, o clique no reiniciar e na bola do jogo, não mais funcionarão para essas ações.
O código finaliza adicionando dentro da forma do menu, um botão para fechamento do menu. Ele também adiciona um evento nesse botão, tornando-o então o único item clicável na interface. O código encerra retornando o objeto de menu recém criado.
A opção de fechar do menu chama a função closeMenu() é mostrada abaixo e simplesmente retira o menu da cena. A função também altera a variável que controla se o jogo está pausado, marcado que ele deixa de estar pausado. Essa variável é marcada como true quando o menu é aberto.
Para praticar: implemente no jogo o recurso de pausar, fazendo com que a bola não se desloque enquanto jogo estiver pausado. |