このエントリーをはてなブックマークに追加   

条件分岐

Pocket

もし○○なら…

次のように入力して実行してみてください。

    screen 0, 640, 480
    HP = 200

    ;5回連続攻撃
    repeat 5
    mes "主人公は70のダメージ!"
    HP = HP – 70
    mes "現在のHPは" + HP + "です\n"
    loop

<実行結果>

主人公は70のダメージ!
現在のHPは130です

主人公は70のダメージ!
現在のHPは60です

主人公は70のダメージ!
現在のHPは-10です

主人公は70のダメージ!
現在のHPは-80です

主人公は70のダメージ!
現在のHPは-150です

この主人公はよほどの強敵に遭遇してしまったらしく、 ボコボコにされてしまいます。

ダメージを受ける処理を5回ループさせている… というのはわかりますね?
「現在のHPは○○です」というメッセージの最後に「\n」と書いてあります。

これは「改行」を意味します。何も書かなくても改行になりますが、これを入れると一行空けることができます。

さて、主人公が弱いのは仕方ないとして、HPがマイナスになってしまうのはプログラム的にどうかと思います。

そこで、HPがマイナスにならないようにしてみたいと思います。

考え方としては、HPから70を引いたあとに、 もしHPが0より小さくなっていたら変数HPに0を代入します。

HSPでは、「もし○○だったら△△する」という処理は

if (○○){
△△
}

 

という書き方をし、これを通称 if文(イフブン)と呼びます。

今回のプログラムはこのように書きます。

    screen 0, 640, 480
    HP = 200

    ;5回連続攻撃
    repeat 5
    mes "主人公は70のダメージ!"
    HP = HP – 70

    ;HPをマイナスにしない 
    if(HP < 0){
        HP = 0
    }

    mes "現在のHPは" + HP + "です\n"
    loop

HP < 0というのはHPが0より小さい・・・
つまりマイナスだということですね。

ここに書いた条件が成り立てば、その下の{ }の中に書いた処理を実行します。
これで、HPが0より小さくなることは無いですね。

条件に影響するのはあくまで{ }内の処理であって、
それ以降のプログラムは何事もなかったように実行されます。

今回の例でいえば、HPがプラスだろうがマイナスだろうが
「現在のHPは○○です」という表示は行われます。

ちなみに、今回は「○より小さかったら」という条件でしたが、
条件の書き方は次のようになります。

書き方 意味
○ < □ ○が□より小さい(未満)
○ > □ ○が□より大きい
○ <= □ ○が□以下(≦とおなじ)
○ >= □ ○が□以上(≧とおなじ)
○ = □ ○と□が同じ
○ ! □ ○と□が違う(≠とおなじ)

 

 

もし ○○じゃなかったら…

さらに追加して、現在のHPを表示したあとに、
まだHPが1以上なら「まだ生きている」と表示し、
そうじゃなかったら(HPが0)「もう死んでいる」と表示するようにしてみましょう。

前半の仕様は問題ないですね。

                :
                :
    ;判定
    if(HP < 0){
        HP = 0
    }

    mes "現在のHPは" + HP + "です\n" 

    ;生死の判定
    if(HP >= 1){
        mes "まだ生きている\n"
    }

    loop

これで良いでしょう。
HP >= 1」 は 「HP > 0」と書いても同じです。

さて、問題はこの次です。

if文の条件が成り立たなかった場合の処理は次のように書きます。

              :
              :
    mes "現在のHPは" + HP + "です\n"

    ;生死の判定
    if(HP >= 1){
        mes "まだ生きている\n"
    }else{
        mes "もう死んでいる\n"
    }
    loop

elseは「○○じゃなかったら」という意味です。

これで、仕様通りに動くはずです。

ちなみに、elseはif文のオプション機能なので、
ifを使わずにelseだけ使うことはできません。

【メモ】
上のプログラムは、elseを使わずに実装することもできます。

if(HP >= 1){
    mes "まだ生きている"
}
if(HP = 0){
    mes "もう死んでいる"
}

と書けばいいですね。
ただし、今回のように必ずどちらかの処理を行う場合は、条件を2つ書くより
elseを使った方がシンプルで、間違いがないと思います。

 

ループの強制終了

現状では、主人公が生きてようが死んでようが、必ず5回攻撃してきます。

さすがにもう死んでいるのに攻撃されるのは惨いので、
途中で死んでしまった場合はループを終了させるようにしましょう。

ループを終了させたいときはbreak命令を使います。

              :
              :
    ;生死の判定
    if(HP >= 1){
        mes "まだ生きている\n"
    }else{
        mes "もう死んでいる\n"
        break
    }
    loop

breakは「ループを終了しなさい」という命令です。この命令もよく使うのでしっかり覚えておいてください。

たとえばゲームでは、タイトル画面で何かボタンを押すと次の画面に切り替わると思います。
これは、タイトルの絵を表示した後に永久ループさせ、ボタンが押されたらbreak という作り方をします。

 

今回のポイント

  • 「もし○○だったら△△する」という処理は
            if(○○){
                △△
            }

    と書く。
  • 「もし○○だったら△△する。そうじゃなかったら××する」という処理は
            if(○○){
                △△
            }else{
                ××
            }

    と書く。
  • ループを途中で終了させる場合はbreakと書く。

 

 

Pocket

変数(後編)

Pocket

計算

「変数」とは言うものの、前ページではHPの値は変わらなかったので、
変数の意味が特にありませんでした。

次はいよいよ変数の値を変えてみたいと思います。
続きを読む

Pocket

変数(前編)

Pocket

定数と変数

ループ処理を学びましたが、それだけではやはり何回実行しても結果は同じです。

ゲームと言うのは
“敵を倒せばスコアが入る” や “攻撃を受ければHPが減る”
のように何らかの値が変化します。
続きを読む

Pocket

ループ

Pocket

人は、1年に1つずつ年齢を重ねていく。
しかし、刻々と流れゆく時間にただ身を任せるわけではなく、
時には同じことを繰り返したり、時には大きな選択を迫られたりする。
そうして人は複雑な人生を歩み、それぞれがちがった結果を残す。

 

さて、Lesson2は哲学のお勉強をします。

嘘です。(そればっかりw)

実は上に書いた中ニくさい文章は、プログラムにも同じことが言えます。

Lesson1で作ったプログラムは、何回実行しても同じ結果が出ますよね?

でも、ゲームはそうじゃありません。
同じゲームを100人の人がプレイしたら、スコアなり、主人公のレベルなり、
所持アイテムなり、最終的にはみんな違う結果になるはずです。

もし、100人とも同じ結果になるのであれば、
それはゲームではなく「映画」になってしまいます。

Lesson1で学習したとおり、
プログラムは基本的に上から1行ずつ順番に実行されます。

しかし、ある条件で違う処理をしたり、
条件を満たすまで処理を繰り返したりします。

例えば、シンプルなアクションゲームの処理を考えてみましょう。

ざっくり描くと、このような流れになるはずです。

  01_01

YES・NOで分岐しながら。全体の処理を繰り返していますね?

Lesson2では、このようなプログラムの流れの変化を学習します。

これができないとゲームが作れません。

「映画」どころか「静止画」しか出せなくなってしまいます。

大して難しいことはありませんので、頑張りましょう。

 

繰り返し

では、同じ処理を繰り返す方法を勉強しましょう。

ちなみにプログラム用語では、繰り返すことを『ループ』と呼びます。

次のようにプログラムを書いてみてください。

    screen 0, 640, 480
    repeat 3
    mes "スライムがあらわれた"
    loop

実行してみると『スライムがあらわれた』が3回表示されます。

「repeat」「loop」は必ずセットで使われる命令で、
「間に書かれた処理を繰り返しなさい」という意味です。

repeatのパラメータは繰り返す回数です。

repeatとloopの間には何行書いても構いません。

なお、repeatとloopの間のプログラムは、
上の例のようにTABキーでもう一段階右にずらしておきます。

そうすることで、どこからどこまでを繰り返すのかが
すぐにわかるようになります。

 

永久ループ

repeatのパラメータを省略すると、どうなるでしょうか。

この場合、必ずawait命令を入れてください。

次のようにします。

    screen 0, 640, 480
repeat
mes "スライムがあらわれた"
await 16
loop

実行してみると、文字の表示が何度も繰り返され画面の外まで表示されます。

画面外に出ても、見えなくなっただけでループは止まりません。

このように、ずっと続くループ処理を永久ループと呼びます。

そして、永久ループに限らずしばらく時間がかかるループ処理を書く場合は
必ずawait命令を間に入れます。

これは「ちょっとだけプログラムを止める」という命令です。

なぜこれを入れなければならないかと言うと・・・・

▼▼▼▼▼▼▼▼混乱する人は読み飛ばしてください▼▼▼▼▼▼▼▼
Windowsというのは常にいろいろなプログラムが同時に動いています。

ネットをしながら音楽を聴いたり、
ネットだって何ページも同時に開けますよね?

何もしてなくても、時計が動いていたり、
マウスが動いていないか監視したりいろいろやってます。

それは、正確に言うと「同時に処理してる」のではなく
「順番に少しずつ処理している」のです。

これを専門用語で「マルチタスク」と言います。

さて、そんな忙しい状況で、HSPで永久ループを書くと
パソコン(CPU)はHSPの処理にかかりっきりになってしまいます。

すると、他の大事な機能を処理する暇が無くなってしまい、
パソコンがフリーズしてしまいます。

パソコンがフリーズしてしまえばHSPの処理も止まってしまい、
どうしようもなくなってしまうのです。

そこで、永久ループの場合は、
ちょっとだけ処理を止めるawait命令を入れます。

すると、HSPが一瞬止まった隙に、他の処理をすることができ、
みんなスムーズに動けます。

ようするに、「譲り合い」ということですね。
▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲▲

さて、await命令のパラメータは、プログラムを停止させる時間です。

単位は「ミリ秒」。

1メートルは1000ミリメートルですよね?

同様に、await 1000と書けば、1秒間止まります。

では、上の例の16という数値はどこから来たのでしょうか。

実はゲームは基本的に1秒間に60回画面を更新します。

1000ミリ秒に60回ってことですね?

ということは、1000÷60≒16.66666・・・・なので、
約16ミリ秒に1回画面を更新していることになります。

今回はそれに合わせてみました。

この講座はゲーム制作を目標にしているので、基本的にawaitは16でいいでしょう。

【メモ】
永久ループでなくても、ある程度時間がかかるループ処理をする場合はawaitが必要になります。
とは言っても、数百回のループであれば(処理内容にもよりますが)一瞬で終わるので、
awaitは必要ありません。

なお、await 16と書けば必ず1秒間に60回ループするとは限りません。
複雑な処理をしたり、性能の低いマシンで実行すれば、それより遅くなることがあります。
ただし、1秒間に60回以上繰り返すことはなくなります。

 

 

今回のポイント

  • repeat 回数 ~ loop の間に書いた処理は 指定した回数繰り返される。

  • 永久ループの場合は、必ずループの中にawait 16を入れる。

Pocket

コメント

Pocket

コメントの書き方

プログラムが長くなってくると、どこで何をやっているのかわからなくなってきます。
そこで・・・

    ;ウィンドウを作成
    screen 0, 640, 480

    ;文字表示
    mes "ゴブリンが現れた!!"
    color 255, 0, 0  ;色指定
    pos 200, 100     ;表示位置指定
    font "MS 明朝", 20, 2    ;フォント指定
    mes "スライムも現れた!!"
    mes "勇者が現れた!!"

続きを読む

Pocket