さて、前回は「レースゲーム」を題材にmicro:bitでゲームのプログラムを作ってみました。
これに気を良くしたので次のお題は「インベーダーゲーム」にしようと思います。
前回同様まだこの時点では完成していないのでもしかしたらリタイアするかもしれません。
インベーダーゲームの概要を考える
まずはインベーダーゲームの概要を考えます。
概要
・ゲーム画面は5×5のLEDを使って宇宙船の真上(宇宙船の真上とは?w)から見下ろしたイメージです。
・前方からインベーダーが横移動しながら下へ迫ってきます。
・インベーダーは宇宙船から発射した弾に当たると倒せます。
・インベーダーが一番下まで来るとゲームオーバーでそれまでに倒したインベーダーの数で勝負するゲームです。
宇宙船の移動を実装
簡単に済ませるためにレースゲームと同じ実装をしました。(これ以外の実装方法を想像できない)
スプライト変数「宇宙船」をX2、Y4に作成してAボタンで左、Bボタンで右に移動するようにプログラムします。
弾の実装
宇宙船は弾を発射してインベーダーを倒します。
そのため宇宙船から発射される弾を実装する必要があります。
弾(スプライト)を作成する
宇宙船と同様に弾の変数を作り、スプライトを作成して弾用のスプライトを作ります。
弾はAボタンとBボタンの同時押しで発射されるように実装するため、スプライトの作成は「最初だけ」ブロックではなく「ボタン「A+B」が押されたとき」ブロックに配置します。
これで宇宙船の前のLEDが点灯し続けるプログラムができました。
あとはこの弾を前方に移動するプログラムが必要です。
弾(スプライト)を自動で前方に移動させる
スプライトの移動を繰り返すには「ずっと」ブロックを使います。
レースゲームの時と同様に一時停止時間を使ってY軸を1つずつずらすように実装してみます。
この実装をしたところ、「failed cast on null」のエラーメッセージが表示されました。
エラーの内容的には「nullへの割り振り失敗」ってところでしょうか?
この内容を頼りに考えると問題は「「弾」の「Y」を「-1」だけ増やす」ブロックの事でスプライト変数「弾」がまだ作られていないのにYの値を増減させようとしているから怒られたと想定できます。(スプライト変数「弾」はAとBボタンの同時押しの時に作成するため)
そのため、スプライト変数「弾」は初期化されてからYを増減するプログラムに組み替える必要があります。
スプライトの存在を判定するブロックが見当たらないので存在を示す変数を作成して対応してみます。
「発射」という変数を使い「1」を発射中、「0」を非発射中として発射中かどうかをこの変数で確認し、発射中のみYを増減できるようにしてみました。
これで発射した弾が一番上で消えるまでのプログラムを実装する事ができました。
|
|
弾が残る問題の対応
宇宙船から発射した弾が前方に飛んでいき、一番上で消えるまで実装できたのですがここで新たな問題が発生しました。
弾が出ている最中に新しい弾を発射しようとすると後から発射した弾にスプライト変数が乗っ取られるらしくその場に留まり制御不能になってしまいます。
そこで今回対応した方法は一度に発射できる弾の数は1発に制限する事にしました。
「ボタン「A+B」が押されたとき」ブロックの処理を発射していない時に限定させました。
これで弾が制御不能になる事がなくなりました。
まとめ
宇宙船の動作は完成しました。
今回はプログラムを組んでいて発生した問題とその対応についても書きました。
ここではサラッと書いていますがいざ問題が発生すると問題の特定は結構大変だと思います。
micro:bitでは細かいデバッグが出来ない(やり方を知らないだけかも)のでここら辺は1つでも多くプログラムする事で当たりがついてくると思います。
その2はこちら
コメント