Estou com grande dificuldade em na hora de montar meu código.
Estou tentando acompanhar os exemplos do Ponto V afim de criar uma animação e o gameLoop.
Na hora de organizar de definir as classes, eu estou um pouco perdido.
Como vocês costumam fazer essa organização de Classes?
Por exemplo, num jogo, é necessário que eu tenha uma classe para cada personagem e para pintura de cada pergonagem?
Ex de classes:
Player (Com infomações do jogador sobre posição)
SpritePlayer (So para pintar o jogador)
Inimigo (Com informações de posição do inimigo)
SpriteInimigo (Só para pintar o inimigo)
Cenario (Com informações do cenário)
TilesCenario (Só para pintar o cenário)
Lógica (Para comparar as ações do jogado com o inimigo)
Eu não sei se é certo fazer isso. Acho que não consigo pegar bem o conceito de OO e aplicá-lo em meus programas.
Tem uma máxima de que ao criar um modelo de jogo os sujeitos do modelo deveriam ser classes e ações deveriam ser métodos. É certo pensar dessa forma? Como vocês se organizam para começar a criar um jogo?
Você está indo no caminho certo, só cuidado para a nomenclatura, para você não se perder. É importante dividir as classes de serviços (Image, Animation, Sound), das classes da lógica do jogo (Player, Enemy, Boss, etc.).
Evite também fazer muita herança, prefira composição. Ao invés de SpritePlayer ser um filho de Player, simplesmente coloque um atributo “Image” dentro da classe Player. Isso deixa o seu modelo mais simples.
Lembre-se de usar a regrinha do “é um” e “tem um”. Um jogador é uma imagem, ou tem uma imagem? Se tem uma, indica uma relação de composição, não herança. Se “é uma” então, provavelmente você terá a relação de herança. Na dúvida, use composição.
É comum, sim, ter uma classe para cada tipo de inimigo no jogo, desde que sua lógica mude. Se o inimigo só fica mais forte, com mais vida ou mais rápido, então é provavel que você vá mexer em um de seus atributos e não na sua lógica, logo, usa-se a mesma classe.
A classe “Lógica” está meio nas nuvens aí. Que tipo de comparação você pensa em fazer com ela?
Seria tipo para comparar se o Jogador deu um golpe em algum inimigo. Mas é justamente isso minha dúvida, não sei como organizar essas idéias.
Supondo que seja um jogo de plataforma.
O cenário teria os atributos e seria desenha todo na classe “Cenário”?
É melhor eu desenhar o Jogador e controlar seus atributos e movimentação pela classe “Player”?
O calculo de “Inimigo encosta em Jogador, Jogador perde energia” seria feito em qual classe (era aqui que eu havia encaixado o “Lógica”)?
E qual a diferença do jogador “Ser uma imagem” ou “Ter uma imagem”?
Vai existir uma classe chamada Level (fase) que controla toda a fase do jogo.
Ela vai pegar todos os objetos de jogo que você tem desenhado e testar se houve colisão entre eles.
Se houver, ela terá que disparar um método em cada GameObject que colidiu, e ele então tomará uma ação.
O protótipo de um código simples disso, seria assim:
[code]
//Processa a lógica de todos
for (GameObject obj : gameObjects()) {
obj.updateLogics();
}
//Teste de colisão
for (int i = 0; i < gameObjects.size()-1; i++)
for (int j = i+1; i < gameObjects.size(); j++) {
//Obtém os dois objetos que testaremos colisão
GameObject obj1 = gameObjects.get(i);
GameObject obj2 = gameObjets.get(j);
//Testa se os dois objetos colidiram
if (obj1.collidedWith(obj2) {
//Avisa os dois objetos que uma colisão ocorreu
obj1.collidesWith(obj1);
obj2.collidesWith(obj1);
}
}
}
//Remove os mortos e pinta os vivos
Iterator it = new Iterator();
while (it.hasNext()) {
GameObject obj = it.next();
if (obj.isDead())
it.remove();
else
obj.renderGraphics(g2d);
}[/code]
Esse código não é muito eficiente, mas é adequado para seus primeiros jogos de plataforma. Isso ficará na classe Game. Note que ele depende que todos os GameObjects do jogo implementem a seguinte interface:
public interface GameObject {
void updateLogics(); //Pinta o objeto do jogo
void renderGraphics(Graphcis2D g2d); //Pinta o objeto do jogo
boolean collidedWith(GameObject other); //Testa se dois objetos colidiram entre si
void collidesWith(GameObject other); //Avisa que uma colisão ocorreu
boolean isDead(); //Retorna true quando esse objeto está morto e deve ser removido do jogo
}
Dê uma olhada nesse tutorial do Coke and Code.
Ele usa esses conceitos de forma rápida:
http://www.cokeandcode.com/spaceinvaderstutorial
Obrigado pela ajuda ViniGodoy. Vou dar uma estudada. =)