J2ME RPG游戏边学边做(一)

juney Post at 2006/8/11 15:24:00

笔者以前是做j2ee的,一个月前由于兴趣所致开始利用业余时间学习j2me游戏开发。在网上看了一通教程后,便准备动手一边学一边做一个简单的rpg游戏。虽然起点比较高,但感觉游戏难度越大,遇到的问题也就越多。这样待全部解决后,也就学的差不多了。另外只有做这种游戏才有学下去的兴趣。以后我会每次把写成的源码及思路发上来,供大家指正。希望各位高人可以无私的帮助我。

  下面是游戏中所需要的部分图片,还有的图片下次写到了再上传:
hero_left.png:

hero_right.png:

hero_up.png:

hero_down.png:

  整个程序的主体在BraveCanvas类中完成,该类继承于GameCanvas实现Runnable接口,由BraveMIDlet类启
动他,BraveMIDlet继承MIDlet实现CommandListener接口。BraveMIDlet类代码如下:(由于只是一个简单的rpg,开头画面和菜单全部省略了,改为由一个按扭启动游戏)

BraveMIDlet.java

package brave;

import javax.microedition.lcdui.*;
import javax.microedition.midlet.*;

public class BraveMIDlet extends MIDlet implements CommandListener
{
 private Display d ;
 private Command exitCommand ;
 private Command startCommand ;

    private BraveCanvas braveCanvas;

 public BraveMIDlet()
 {
  d = Display.getDisplay(this);
  exitCommand = new Command("退出",Command.EXIT,1);
  startCommand = new Command("开始",Command.SCREEN,1);
 }

 public void startApp()
 {
  //创建BraveCanvas
  braveCanvas = new BraveCanvas();
  braveCanvas.addCommand(exitCommand);
  braveCanvas.addCommand(startCommand);
  braveCanvas.setCommandListener(this);
  //装载BraveCanvas
  d.setCurrent(braveCanvas);
 }

 public void pauseApp()
 {
 }

 public void destroyApp(boolean unconditional)
 {
 }

 public void commandAction(Command c , Displayable dpa)
 {

  String str_co = c.getLabel();
  if(str_co.equals("开始"))
  {
   //运行BraveCanvas中的线程(启动游戏)
   braveCanvas.startup();
  }
  else if(str_co.equals("退出"))
  {
   destroyApp(false);
   notifyDestroyed();
  }
 }
}

BraveCanvas.java

package brave;

import javax.microedition.lcdui.game.GameCanvas;
import javax.microedition.lcdui.Graphics;
import java.io.IOException;

public class BraveCanvas extends GameCanvas implements Runnable
{
 private boolean sign;
 private Graphics g;
 //设置@符号的当前位置
 private int x,y;
 public BraveCanvas()
 {
  super(true);
  //初始化@位置
  x = getWidth()/2;
  y = getHeight()/2;
 }
 
 public void startup()
 {
  this.sign = true;
  Thread thread = new Thread(this);
  //启动线程
  thread.start();
 }

 public void run()
 {
  g = getGraphics();
  while(sign)
  {
   try
   {
    //@符号的移动
    input(g);
    //@符号的显示
    paint(g);
    //这里应该有详细的计算,方便为上,置为15
    Thread.sleep(15);
   }
   catch(Exception e)
   {
    System.out.println("2:"+e);
   }
  }
 }

 public void input(Graphics g) throws IOException
 {
  int keystates = getKeyStates();
  switch(keystates)
  {
   case UP_PRESSED:
    y = Math.max(0, y - 1);
    break;
   case DOWN_PRESSED:
    y = Math.min(getHeight(), y + 1);
    break;
   case LEFT_PRESSED:
    x = Math.max(0, x - 1);
    break;
   case RIGHT_PRESSED:
    x = Math.min(getWidth(), x + 1);
    break;
  }
 }

 public void paint(Graphics g)
 {
  //设置画布的背景色
  g.setColor(0x000000);
  //把背景色画满画布
  g.fillRect(0, 0, getWidth(), getHeight());
  //设置画布的前景色
  g.setColor(0xffffff);
  //在画布上写上@
  g.drawString("@", x, y, Graphics.TOP|Graphics.LEFT);
  //刷新画布
  flushGraphics();
 }
}

上面代码运行后,画面上会出现一个"@"字符随着键盘的左右而移动。虽然这离rpg游戏相差很远,但这是一
个游戏的基本框架。下面我们要做的就是把"@"换成我们的英雄。为了程序清晰,我们还要设计一个英雄类
Hero,该类继承于Sprite,这个类里面要用到上面的图片。

Hero.java

package brave;

import javax.microedition.lcdui.game.Sprite;
import javax.microedition.lcdui.Image;
import java.io.IOException;

public class Hero extends Sprite
{
 //设置英雄的当前位置
 private int x, y;
 private BraveCanvas braveCanvas;

 public Hero(Image image, int frameWidth, int frameHeight)
 {
  //英雄的初始化
  super(image, frameWidth, frameHeight);
 }

 public void setBraveCanvas(BraveCanvas braveCanvas)
 {
  this.braveCanvas = braveCanvas;
 }

 public void init(int x, int y)
 {
  //英雄位置的初始化
  this.x = x;
  this.y = y;
 }

 public void afresh()
 {
  //刷新英雄的位置
  setPosition(this.x, this.y);
 }

 public void moveUp() throws IOException
 {
  //英雄上移,并改为相应的图片
  setImage(Image.createImage("/hero_up.png"), 17, 26);
  nextFrame();
  this.y = Math.max(0, y - 1);
 }

 public void moveDown() throws IOException
 {
  //英雄下移,并改为相应的图片
  setImage(Image.createImage("/hero_down.png"), 17, 26);
  nextFrame();
  this.y = Math.min(braveCanvas.getHeight(), y + 1);
 }

 public void moveLeft() throws IOException
 {
  //英雄左移,并改为相应的图片
  setImage(Image.createImage("/hero_left.png"), 17, 26);
  nextFrame();
  this.x = Math.max(0, x - 1);

 }

 public void moveRight() throws IOException
 {
  //英雄右移,并改为相应的图片
  setImage(Image.createImage("/hero_right.png"), 17, 26);
  nextFrame();
  this.x = Math.min(braveCanvas.getWidth(), x + 1);
 }

}

然后把BraveCanvas类稍做修改,把"@"换成英雄

BraveCanvas.java

package brave;

import javax.microedition.lcdui.game.GameCanvas;
import javax.microedition.lcdui.Graphics;
import java.io.IOException;
import javax.microedition.lcdui.Image;

public class BraveCanvas extends GameCanvas implements Runnable
{
 private boolean sign;
 private Graphics g;
 private Hero hero;
 public BraveCanvas()
 {
  super(true);
 }
 
 public void startup()
 {
  this.sign = true;
  try
  {
   Image heroimage = Image.createImage("/hero_up.png");
   hero = new Hero(heroimage, 17, 26);
   hero.setBraveCanvas(this);
   hero.init(40,40);
  }
  catch(Exception e)
  {
   e.printStackTrace();
  }

  Thread thread = new Thread(this);
  thread.start();
 }

 public void run()
 {
  g = getGraphics();
  while(sign)
  {
   try
   {
    input(g);
    paint(g);
    Thread.sleep(15);
   }
   catch(Exception e)
   {
    System.out.println("2:"+e);
   }
  }
 }

 public void input(Graphics g) throws IOException
 {
  int keystates = getKeyStates();
  switch(keystates)
  {
   case UP_PRESSED:
    hero.moveUp();
    break;
   case DOWN_PRESSED:
    hero.moveDown();
    break;
   case LEFT_PRESSED:
    hero.moveLeft();
    break;
   case RIGHT_PRESSED:
    hero.moveRight();
    break;
  }
  hero.afresh();
 }

 public void paint(Graphics g)
 {
  g.setColor(0x000000);
  g.fillRect(0, 0, getWidth(), getHeight());
  g.setColor(0xffffff);
  hero.paint(g);
  flushGraphics();
 }
}

这样,我们的英雄就可以在画面上移动了,不过英雄比较简单,没有hp,mp等等,只是一个图片。而且如果大
家感觉英雄的脚步过快,可以在BraveCanvas类中的Hero初始化时设置:
hero.setFrameSequence(new int[]{0, 0, 1, 1, 0, 0, 2, 2 });

已有 0 位网友发表了看法