Já vimos como mostrar gráficos na nossa tela, agora iremos ver algo mais relacionado ao desenvolvimento de jogos em 2D utilizando as classes TiledLayer, Sprite e LayerManager.
Tiles podem ser compreendidos como blocos usados para a construção de cenários estáticos em jogos 2D, a técnica de construção usando Tiles é praticamente a mesma em qualquer plataforma, cria-se um objeto e utiliza-se um vetor para posicionar os Tiles no cenário. Sprites são os seres dinâmicos do jogo como personagens, inimigos, objetos móveis, etc. No J2ME temos a classe LayerManager que serve para controlar e mostrar o mundo do jogo construído através de Tiles e Sprites.
TiledLayer
editarVamos começar utilizando a mesma estrutura do GameCanvas.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Primeiramente precisamos carregar a imagem onde estão desenhados os tiles, para isso vamos instanciar e criar o objeto do tipo Image como vimos anteriormente.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora vamos instanciar a variável do tipo TiledLayer.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
TiledLayer meuTiledLayer;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora dentro do método run() vamos criar o objeto TiledLayer, vamos entrar com 4 parâmetros: O primeiro é a quantidade de linhas que o cenário vai ter. O segundo é q quantidade de colunas que o cenário vai ter. O terceiro é o objeto Image carregado. O quarto é a largura em pixels de cada tile. O quinto é a altura em pixels de cada tile.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
TiledLayer meuTiledLayer;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagem, 16, 16);
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora para vamos criar o vetor para desenharmos a grade de tiles, para isso devemos criar um vetor do tipo int[] e colocar o valor correspondente ao tile, lembre-se que no nosso exemplo usamos uma grade de no máximo 5x5 tiles.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
TiledLayer meuTiledLayer;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagem, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora com o vetor da grade já criado, devemos inseri-lo dentro do objeto TiledLayer, a inserção é feita através do método setCell() onde inserimos cada célula individualmente, para isso vemos criar um laço for criando uma variável de zero até menor que grade.length.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
TiledLayer meuTiledLayer;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagem, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
for(int i=0; i<grade.length; i++){
}
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora dentro do laço for vamos finalmente usar o método setCell() da classe TiledLayer utilizando os seguintes atributos: Primeiro a linha em que está sendo inserido. Segundo a coluna em que está sendo inserido. Terceiro o valor do tile (a célula do vetor grade[]).
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
TiledLayer meuTiledLayer;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagem, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
for(int i=0; i<grade.length; i++){
meuTiledLayer.setCell(i%6, i/6, grade[i]);
}
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Sprite
editarSprites são imagens com animação geralmente usados como personagens, inimigos ou objetos móveis, vamos ver como implementa-los no J2ME. Inicialmente vamos carregar a imagem onde está desenhado o Sprite, para isso vamos instanciar e criar um objeto do tipo Image como vimos anteriomente.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora vamos instanciar a variável do tipo Sprite.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
Sprite meuSprite;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora dentro do método run() vamos criar o objeto do tipo Sprite, vamos entrar 3 parâmetros: Primeiro o objeto do tipo Image. Segundo a largura em pixels de cada cena. Terceiro a altura em pixels de cada cena.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagem;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagem = minhaImagem.createImage("/Minha Imagem.png");
meuSprite = new Sprite(minhaImagem, 32, 32);
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
LayerManager
editarVimos como carregar e criar Tiles e Sprites, agora vamos ver como coloca-los para serem exibidos na tela, para isso iremos ver como usar o LayerManager. Para começar vamos instanciar e inicializar os objetos do tipo TiledLayer e Sprite vistos anteriormente.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagemTile;
TiledLayer meuTiledLayer;
Image minhaImagemSprite;
Sprite meuSprite;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagemTile = minhaImagemTile.createImage("/Minha Imagem tile.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagemTile, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
for(int i=0; i<grade.length; i++){
meuTiledLayer.setCell(i%6, i/6, grade[i]);
}
minhaImagemSprite = minhaImagemSprite.createImage("/Minha Imagem sprite.png");
meuSprite = new Sprite(minhaImagemSprite, 32, 32);
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora para começarmos a controlar a exibição de Tiles e Sprites primeiramente devemos instanciar uma variável do tipo LayerManager.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagemTile;
TiledLayer meuTiledLayer;
Image minhaImagemSprite;
Sprite meuSprite;
LayerManager meuLayerManager;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagemTile = minhaImagemTile.createImage("/Minha Imagem tile.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagemTile, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
for(int i=0; i<grade.length; i++){
meuTiledLayer.setCell(i%6, i/6, grade[i]);
}
minhaImagemSprite = minhaImagemSprite.createImage("/Minha Imagem sprite.png");
meuSprite = new Sprite(minhaImagemSprite, 32, 32);
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora dentro do run() vamos criar o objeto do tipo LayerManager
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagemTile;
TiledLayer meuTiledLayer;
Image minhaImagemSprite;
Sprite meuSprite;
LayerManager meuLayerManager;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagemTile = minhaImagemTile.createImage("/Minha Imagem tile.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagemTile, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
for(int i=0; i<grade.length; i++){
meuTiledLayer.setCell(i%6, i/6, grade[i]);
}
minhaImagemSprite = minhaImagemSprite.createImage("/Minha Imagem sprite.png");
meuSprite = new Sprite(minhaImagemSprite, 32, 32);
meuLayerManager = new LayerManager();
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora vamos colocar organizar os objetos do tipo Sprite e TiledLayer para serem exibidos, para isso vamos usar o método append() da classe LayerManager, note que quando se pintar a tela a ordem dos elementos inseridos irá influenciar o que será exibido em cima do outro, sempre o primeiro objeto colocado no append() será o que ficará sempre visível, nesse exemplo vamos insrir na ordem, meuSprite -> meuTile.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagemTile;
TiledLayer meuTiledLayer;
Image minhaImagemSprite;
Sprite meuSprite;
LayerManager meuLayerManager;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagemTile = minhaImagemTile.createImage("/Minha Imagem tile.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagemTile, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
for(int i=0; i<grade.length; i++){
meuTiledLayer.setCell(i%6, i/6, grade[i]);
}
minhaImagemSprite = minhaImagemSprite.createImage("/Minha Imagem sprite.png");
meuSprite = new Sprite(minhaImagemSprite, 32, 32);
meuLayerManager = new LayerManager();
meuLayerManager.append(meuSprite);
meuLayerManager.append(meuTile);
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}
Agora colocaremos a cena para ser exibida na tela, dentro do loop principal vamos usar o método paint() da classe LayerManager e entrar como parâmetros: 1º o objeto do tipo Graphics. 2º o pixel x de onde a cena começará a ser exibida. 3º o pixel y de onde a cena começará a ser exibida.
import javax.microedition.lcdui.game.*;
import javax.microedition.lcdui.*;
public class MeuGameCanvas extends GameCanvas implements Runnable {
Thread meuThread;
Graphics meuGrafico = this.getGraphics();
Image minhaImagemTile;
TiledLayer meuTiledLayer;
Image minhaImagemSprite;
Sprite meuSprite;
LayerManager meuLayerManager;
public MeuGameCanvas(){
super(false);
meuThread = new Thread(this);
meuThread.start();
}
public void run(){
try{
minhaImagemTile = minhaImagemTile.createImage("/Minha Imagem tile.png");
meuTiledLayer = new TiledLayer(5, 5, minhaImagemTile, 16, 16);
int grade[] = { 2, 1, 1, 1, 3,
1, 0, 0, 0, 1,
1, 0, 1, 0, 1,
1, 0, 0, 0, 1,
4, 1, 1, 1, 5 };
for(int i=0; i<grade.length; i++){
meuTiledLayer.setCell(i%6, i/6, grade[i]);
}
minhaImagemSprite = minhaImagemSprite.createImage("/Minha Imagem sprite.png");
meuSprite = new Sprite(minhaImagemSprite, 32, 32);
meuLayerManager = new LayerManager();
meuLayerManager.append(meuSprite);
meuLayerManager.append(meuTile);
}catch(Exception ex){
ex.printStackTrance();
}
boolean fimDeJogo = false;
while(fimDeJogo == false){
try{
meuLayerManager.paint(meuGrafico, 0, 0);
meuThread.sleep(50);
}(catch Exception minhaEscessao){
minhaExcessao.printStackTrance();
}finally{
flushGraphics();
}
}
}
}