Um jogo simples, descomprometido e maroto descobrir sobre a secreta vida animal.
O projeto deve ser entregue como um Pull Request (veja
[1] e [2]) neste repositório.
Ou seja, você deve fazer um fork e, no branch master
, você deve
criar os dois microjogos.
Siga os passos:
git branch -b sandy-junior
.leandro-leonardo
) para o branch master
do professor.Veja alguns detalhes sobre a implementação do jogo a seguir.
O jogo possui algumas telas, como de splash (inicial), menu principal e
"de jogo", e o código referente a cada uma reside em uma classe que herda de
BaseScreen
.
As classes do projeto estão modularizadas nos seguintes pacotes:
br.cefetmg.games
: classes de inicialização e configuração geral do jogo.br.cefetmg.games.graphics
: classes com utilitários gráficos.br.cefetmg.games.logic.chooser
: classes de utilidade para a lógica de jogo.br.cefetmg.games.minigames
: classes referentes aos microgames.br.cefetmg.games.minigames.factories
: classes referentes às fábricas
abstratas que são responsáveis por instanciar os microgames.br.cefetmg.games.minigames.util
: classes utilitárias aos microgames.br.cefetmg.games.screens
: classes referentes às telas do jogo.Os assets (recursos gráficos e de áudio) do jogo ficam na pasta core/assets
:
Os assets de cada microgame devem estar dentro de uma pasta cujo nome é
o nome dele, sem maiúsculas e acentuação, com hífen separando as palavras,
caso haja mais de uma (e.g., assets/shoot-the-caries
).
Para os microgames, estamos usando um gerenciador de assets para pré-carregá-los de forma que, quando da execução da sequência de microgames, o jogo não pára para carregar os recursos e isso dá uma experiência de jogo melhor.
Para usar o gerenciador, supondo que você está criando um SuperMicroJogo
,
cada microgame deve ser implementado em 2 passos:
Declarar de quais assets ele precisa, na classe SuperMicroJogoFactory
.
Por exemplo:
public class SuperMicroJogoFactory implements MiniGameFactory {
// ...
@Override
public Map<String, Class> getAssetsToPreload() {
return new HashMap<String, Class>() {
{
put("super-micro-jogo/personagem.png", Texture.class);
put("super-micro-jogo/tiro.wav", Sound.class);
}
};
}
}
Solicitar os assets já carregados ao gerenciador, na classe do microgame propriamente dito. Por exemplo:
public class SuperMicroJogo extends MiniGame {
private Texture texturaPersonagem;
private Sound somTiro;
public SuperMicroJogo(BaseScreen screen,
GameStateObserver observer, float difficulty) {
super(screen, difficulty, 10000,
TimeoutBehavior.FAILS_WHEN_MINIGAME_ENDS, observer);
}
@Override
protected void onStart() {
this.texturaPersonagem = screen.assets.get(
"super-micro-jogo/personagem.png", Texture.class);
this.somTiro = screen.assets.get(
"super-micro-jogo/tiro.wav", Sound.class);
// ...
}
// ...
}
Após criar classes que herdam de MiniGame
e MiniGameFactory
, você
deve ir até PlayingGamesScreen
e alterar o construtor de GameSequencer
para receber as factories dos seus microgames.
Nota: para ver como o pré-carregamento está sendo feito, procure na classe
GameSequencer
.
Como muito bem lembramos da queridíssima aula de Computação Gráfica, uma aplicação em OpenGL possui pelo menos 2 sistemas de coordenadas extremamente importantes:
Em jogos digitais, qual deve ser o comportamento quando um usuário redimensiona a janela? Há pelo menos 3 possibilidades:
É possível e bem simples fazer qualquer uma dessas formas na LibGDX. Optamos pela forma (2) porque ela permite que usemos valores virtuais para largura e altura da tela... como assim?
Podemos ver 3 constantes importantes em Config.java
:
public class Config {
/**
* A largura do mundo de jogo.
*
* Todos os objetos (sprites, etc.) devem estar contidos em coordenadas x
* que vão de 0 a WORLD_WIDTH para que apareçam na tela.
*/
public static final int WORLD_WIDTH = 1280;
/**
* A altura do mundo de jogo.
*
* Todos os objetos (sprites, etc.) devem estar contidos em coordenadas y
* que vão de 0 a WORLD_HEIGHT para que apareçam na tela.
*/
public static final int WORLD_HEIGHT = 720;
public static final float DESIRED_ASPECT_RATIO
= (float) WORLD_WIDTH / (float) WORLD_HEIGHT;
// ...
}
Repare na figura a seguir. Podendo considerar que o sistema de coordenadas do mundo é sempre x E [0,1280] e y E [0,720], fica fácil posicionar os elementos de forma que eles estarão aonde queremos independente da resolução atual da janela do jogo.