J2ME RPG游戏边学边做

J2ME RPG游戏边学边做(五)–游戏灵魂(计时器和奖惩与评价)

    我们该加入我们的计时器了,我要从游戏开始时刻开始计时,并不断的更新到屏幕上,在游戏结束后计时器要停止工作。

    
首先在初始化的时候将当前时刻记录下来:

gametime=0;
gametimeoffset=System.currentTimeMillis();

以后只要游戏不gameover就在每个更新周期都进行一次计算:
gametime=(System.currentTimeMillis()-gametimeoffset)/1000;
//转换为秒

下面要做的就是将它显示出来,还记得我们曾经实现的字体类了吗,这下子有用了,首先是实例化一个字体类:
img=ImageTools.getImage("/pic/b_number.png");
fontbig=new   Font(g,img,10,15,
new char[]{‘0′,’1′,’2′,’3′,’4′,’5′,’6′,’7′,’8′,’9’});

然后就是显示:
fontbig.drawString(String.valueOf(gametime),screenwidth/2-15,10);

还真是方便yeah!

接着是奖励系统,我们规定每过20s就加一个bomb给玩家。
int awardindex=(int)gametime/20;//计算奖励时间
    if(awardindex>bombawardtop)
      awardindex=bombawardtop;
    if(bombaward[awardindex]!=0){//如果本20s没有奖励
      bombnum+=bombaward[awardindex];
      bombaward[awardindex]=0;//奖励过了
}

尽可能简单和给出些提示是我写本文的原则, 所以评价系统,很easy。
我们建立一个辅助类,提供一个方法,输入游戏时间,返回一个String评语。

public class StringTools {
  protected StringTools() {
  }
  public static String timeOpinion(long gametime){
    if(gametime<10){
      return "Do you play with your foot?";
      //return "i can’t belive,your are a game master";
    }else if(gametime<16){
      return "come boy, you can do it!";
    }else if(gametime<20){
      return "what a pity! try again.";
    }else if(gametime<25){
      return "very well, you are a real man.";
    }else if(gametime<30){
      return "i know you have talent of this game.";
    }else if(gametime<40){
      return "i can’t belive, your are a game master.";
    }else{
      return "oh my god, are you a human?";
    }
  }
}
之后显示出来就好了,我手头没有合适大小的字体图片,我直接使用
g.drawString(StringTools.timeOpinion(gametime),5,22,g.LEFT|g.TOP);

想在手机小小的屏幕容下那么东西是挺费劲的,其实这也是我对手机上玩游戏没什么兴趣,不过我对手机网络应用冲满了信心

J2ME RPG游戏边学边做(六)–莱克兄弟的第一架飞机

实在是等不及了吧?加把劲,让我们加入游戏的主角飞机吧。

你可以将这个游戏定位在动作游戏,一个动作游戏需要不断的从用户端获得输入,基本上不间断,所以plane需要不断的改变位置。那么这个基于桢的游戏应该定在多少桢合适呢?这需要在手机中测试,在模拟器上,如果定在15-18桢左右,是比较合适的。听csdn的几位xd说有的游戏仅仅定在12桢,所以不同的游戏是不一定的。基本上动作游戏对机子的要求是要高一点。我们的游戏框架是线性的,即输出显示和接受输入是在同一个线程中,15桢以下的游戏处理输入会显得比较苯,高于20桢如果处理器速度较慢,很容易出现输入卡在缓冲区,处理不过来的情况。现阶段尽量让桢数降下来吧,你不能和pc上用dx编程时,统一 30fps的情况相提并论。

在这个以控制精灵移动为主要内容的游戏中,我们不封装任何的游戏事件,我们的程序可能有些稚嫩,没关系,一步一步来吧。

1. 飞机

plane是一个标准的plane。由三桢画面组成,首先在ps中处理,让其透明:

在构造函数中,我们加入对飞机的初始化对象语句:

Image img=ImageTools.getImage("/pic/MyPlaneFrames.png");
plane=new GameObject(img,24,24);
      
在gameInit()中初始化状态,位置居中:
plane.reset();
plane.moveto((screenwidth-plane.sprite.getWidth())/2,
(screenheight-plane.sprite.getHeight())/2);

   在gameMain中加入:
plane.paint(g);
   接下来,让飞机在控制下移动,主要是在gameMain中加入输入处理,如果飞机左移就更新画面到飞机左倾的画面,如果飞机右倾反之,没有输入的时候让飞机处于正常。
if (gameover) {
}else{
       if (keyevent) {
        if(key_up){
          plane.move(0, -3);
          plane.sprite.setFrame(0);
        }
        if(key_down){
          plane.move(0, 3);
            plane.sprite.setFrame(0);
        }
        if(key_left){
          plane.move( -3, 0);
          plane.sprite.setFrame(1);
        }
        if(key_right){
          plane.move(3, 0);
          plane.sprite.setFrame(2);
        }
        if(key_fire){
          }
        }
      }
      else {
        plane.sprite.setFrame(0);
      }
}
   尽管很简单,但这是控制精灵移动的主要方式。可以想象一下,如果往左飞不是简单的一桢画面而是播放动画,该怎么实现呢?我们的GameObject功能有限,没有对spriite的动画序列进行增强,今后我们可以增强GameObject,使其支持多个动画序列,弥补spriite的不足。现在逐渐体会到一个好的游戏引擎是多么重要了吧…
      

2. 背景

   让飞机在海面飞行吧,我们用一个蓝色的背景图片代表海面,我们需要他铺满整个背景。我们使用TiledLayer来绘画背景。

初始化:
img=ImageTools.getImage("/pic/back_water.png");
int backcolumns=screenwidth/img.getWidth()+1;//计算横向
int backrows=screenheight/img.getHeight()+1;
background=new TiledLayer(backcolumns,backrows,img,img.getWidth(),img.getHeight());
int x,y;
for (int i = 0; i < backcolumns*backrows; i++) {
   x=i%backcolumns;
   y=i/backcolumns;
   System.out.println("x="+x+" y="+y);
   background.setCell(x,y,1);
}

接下来在gameMain中加入绘制语句。
background.paint(g);//draw background

注意,要保证背景的绘制在飞机的绘画之前。如果使用Layermanager可以很方便的的控制绘制层,但是我们的接下来的子弹要求多个子弹对象共用一个 sprite的图像,但是Layermanager绘画的时候以Layer为单位,由Layermanager帮助我们调用各个layer的paint, so一次只支持将一个sprite画在一个地方,所以我觉得Layermanager有些鸡肋。一般时候我们还是自己paint吧。当然,层是一个很重要的概念,利用层,屏幕校准将非常方便,震动整个屏幕等特效将很实现。也许你有个好法,可以让我不在Layermanager层与sprite状态对象组之间矛盾…

飞行战机源代码: