J2ME游戏之旅(3): 记录存储

    记录存储依赖于一个J2ME的专门的类:RecordStore,位于 javax.microedition.rms.*
 
 我们现在关注一下RecordStore的本质,我们可以可以把它看作一个数据表,但是我们不能直接访问到制定列,必须先使用byte[] getRecord取得某行数据,然后对这个byte[]通过StreamReader来顺序地读到这一列。
   
    它的方法有一大堆,但实际上我们用不着那么多,这里有个BaseRMS类,可以提供方便的借口,代码来自Jason Lam的<J2ME & Gaming>。


import javax.microedition.rms.*;

abstract public class BaseRMS {
   
    private String rmsName;
   
    private RecordStore recordStore;
   
    BaseRMS(String rmsName){
        this.rmsName  = rmsName;         //设置记录名称
    }
   
    public void open() throws Exception {

  // 如果load RecordStore失败则重新生成一个RecordStore
        try {
            recordStore = RecordStore.openRecordStore(this.rmsName,true); 
            if(recordStore.getNumRecords()>0){
                loadData();
            } else {
                createDefaultData();
            }
        }catch(Exception e){
            throw new Exception(this.rmsName + "::open::" + e);
        }
    }

    public void close() throws Exception {
        if(recordStore!=null){
            try {
                recordStore.closeRecordStore();
            }catch(Exception e){
                throw new Exception(this.rmsName + "::close::" + e);
            }
        }
    }
   
    public RecordStore getRecordStore(){
        return this.recordStore;                                  //返回整块记录
    }
   
    public String getRMSName(){
        return this.rmsName;
    }
   
    abstract void loadData() throws Exception;
    abstract void createDefaultData() throws Exception;
    abstract void updateData() throws Exception;

}

下面的Score类由以上的BaseRMS派生


import java.io.*;


public class Score extends BaseRMS {
   
    private String[] names = new String[3];   // 仅保存前三条记录,所以只要一个3元素的数组即可
   
    private int[] values = new int[3];
   
    public Score(String rmsName){
        super(rmsName);        
        initValues();                                            // 这个是初始数据
    }
   
    private void initValues(){
        names[0] = "Magic.D";
        names[1] = "Tangel";
        names[2] = "Nick";
        values[0] = 100;
        values[1] = 50;
        values[2] = 10;
    }
   
    public void loadScores() throws Exception {
        try{
            this.open();
            if(this.getRecordStore()!=null)
                this.close();
        }catch(Exception e){
            throw new Exception("Error loading Scores" + e);
        }
    }
   
    public int[] getValues(){
        return this.values;            // 得到分数的数组
    }
   
    public String[] getNames(){
        return this.names;           // 得到名字的数组
    }
   
    public void reset() throws Exception {    // 重新初始化数据集
        this.open();
        initValues();
        updateData();
        if(this.getRecordStore()!=null)
            this.close();
    }
   
    public void updateScores(int score,String Name) throws Exception {  
        try {   //数据量小,简单地使用冒泡排序来完成更新并重排记录
            for(int i=0;i<names.length;i++){
                if(score>=values[i]){
                    this.open();
                    for(int j=names.length-1;j>i;j--){
                        values[j] = values[j-1];
                        names[j] = names[j-1];
                    }
                    this.values[i] = score;
                    this.names[i] = Name;
                    updateData();
                    if(this.getRecordStore()!=null)
                        this.close();
                    break;
                }
            }
        }catch(Exception e){
            throw new Exception(this.getRMSName() + "::updateScores::" + e);
        }
    }
   
    public boolean isHighScore(int score) throws Exception {
        boolean isHighScore = false;   // 遍历记录,判断新的分数是否是高分
        try {
            for(int i=0;i<names.length;i++){
                if(score>=values[i])
                    isHighScore = true;
            }
        }catch(Exception e){
            throw new Exception(this.getRMSName() + "::isHighScore::" + e);
        }
        return isHighScore;
    }
   
    protected void loadData() throws Exception {
        try {
            for(int i=0;i<names.length;i++){
                byte[] record = this.getRecordStore().getRecord(i+1);
                DataInputStream istream = new DataInputStream(new ByteArrayInputStream(record,0,record.length));  // 注意DataInputStream的使用
                values[i] = istream.readInt();
                names[i] = istream.readUTF();
            }
        }catch(Exception e){
            throw new Exception(this.getRMSName() + "::loadData::" + e);
        }
    }
   
    protected void createDefaultData() throws Exception {
        try{
            for(int i=0;i<names.length;i++){
                ByteArrayOutputStream bstream = new ByteArrayOutputStream(12);
                DataOutputStream ostream = new DataOutputStream(bstream);
                ostream.writeInt(values[i]);
                ostream.writeUTF(names[i]);
                ostream.flush();
                ostream.close();
                byte[] record = bstream.toByteArray();
                this.getRecordStore().addRecord(record,0,record.length);
            }
        }catch(Exception e){
            throw new Exception(this.getRMSName() + "::createDefaultData::" + e);
        }
    }
   
    protected void updateData() throws Exception {
        try{
            for(int i=0;i<names.length;i++){
                ByteArrayOutputStream bstream = new ByteArrayOutputStream(12);
                DataOutputStream ostream = new DataOutputStream(bstream);
                ostream.writeInt(values[i]);
                ostream.writeUTF(names[i]);
                ostream.flush();
                ostream.close();
                byte[] record = bstream.toByteArray();
                this.getRecordStore().setRecord(i+1,record,0,record.length);
            }
        }catch(Exception e){
            throw new Exception(this.getRMSName() + "::updateData::" + e);
        }
    }
   
}

有了这个类,怎么显示高分,怎么加入高分我想应该不用多言了,都是简单的问题啦,同时我们也可以联想到,游戏设置其实跟这个本质上是相同的,我们用BaseRMS派生出一个GameOption类,然后每次进入游戏前读入设置,就OK 。到此我把这个小游戏的各个方面都说了一遍,自我感觉还是比较乱的,我计划接下来再写文章分别仔细讨论一下J2ME的UI设计,图形设计。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值