人工知能に関する断創録

このブログでは人工知能のさまざまな分野について調査したことをまとめています(更新停止: 2019年12月31日)

勇者は壁にぶつかった

勇者が壁にぶつかるようにしてみます。あっ、別に挫折するわけじゃないですよ(笑)

rpg04.jar

壁にぶつかる処理

壁にぶつかる=壁のあるマスには移動できないようにするということです。なので、前回勇者の移動処理を書いていたkeyPressed()から見てみます。

    public void keyPressed(KeyEvent e) {
        // 押されたキーを調べる
        int keyCode = e.getKeyCode();

        switch (keyCode) {
            case KeyEvent.VK_LEFT :
                // 左キーだったら勇者を1歩左へ
                x--;
                break;
            case KeyEvent.VK_RIGHT :
                // 右キーだったら勇者を1歩右へ
                x++;
                break;
            case KeyEvent.VK_UP :
                // 上キーだったら勇者を1歩上へ
                y--;
                break;
            case KeyEvent.VK_DOWN :
                // 下キーだったら勇者を1歩下へ
                y++;
                break;
        }

        // 勇者の位置を動かしたので再描画
        repaint();
    }

前回は各caseの中で直接勇者の座標(x,y)を変化させていましたが、今回はmove()というメソッドを使うことにします。move()は引数としてLEFT、RIGHT、UP、DOWN(定数として宣言してある)を取り、その方向に移動できる場合のみ移動するメソッドです。

    private void move(int dir) {
        // dirの方向でぶつからなければ移動する
        switch (dir) {
            case LEFT:
                if (!isHit(x-1, y)) x--;
                break;
            case RIGHT:
                if (!isHit(x+1, y)) x++;
                break;
            case UP:
                if (!isHit(x, y-1)) y--;
                break;
            case DOWN:
                if (!isHit(x, y+1)) y++;
                break;
        }
    }

move()の中では勇者の座標(x,y)を変更する前に移動先の座標にぶつかるもの(壁)があるかないかをisHit()で調べています。 isHit()は引数の座標にぶつかるものがあったらtrue、なかったらfalseを返すメソッドです。移動先にぶつかるものがない場合のみ勇者を移動させています。ぶつかった場合はif文の中身が実行されないので移動しない点に注意してください。

    private boolean isHit(int x, int y) {
        // (x,y)に壁があったらぶつかる
        if (map[y][x] == 1) {
            return true;
        }
        
        // なければぶつからない
        return false;
    }

壁はmapの中で1で表現してたことを思い出してください。壁以外にぶつかるもの(勇者以外のキャラクターや岩山など)を追加した場合でもこのメソッド内でチェックすれば大丈夫です。

これで勇者はこの城に閉じ込められました。餓死しないうちに出口を作ってやらねば(笑)