問題が判明した落下人の処理を作り直す。
それぞれの落下人の位置を文字列で表す方針は変えない。
同時に全部動かすなら、先頭の一文字を処理して末尾に回す必要はない。代わりに文字数分、ループして処理を行う。
文字列を取り出す、書き込むのは、文字列操作関数を使うのではなく、peek命令と、poke命令で行うのが良さそうと判断。peek、pokeと聞くと、なんだかマシン語みたいと思った。
実際にはバイト単位でのリードライトなので、その感想はある意味正しかった。
困ったのは、HSPにはタイマーによる割り込みイベントがないこと。ON TIMER GOSUBというようなBASIC的な命令があると思ったのだが…
拡張モジュールを使えばありそうなのだが、そこまでは求めないことにした。
BASIC!で採用した、タイマー割込みでの処理ではなく、別の方法を考える。
今は一つのループが、約1/60秒単位で進むようにしているが、これを1サイクルにすると早すぎるため、1ループごとに加算するカウンタを作り、それを特定の数値で割った余りが0の時に、落下人の移動処理を実行するようにした。
救助隊の移動操作は、全ループ中受け付けるので、落下人よりも救助隊の方を理論上早く動かせるはず。
特定の数値を変数として定義しておき、得点の増加とともに、減算していけば、サイクルがどんどん短くなって、落下スピードを早くできるようにもなる。
救急車に入って、ランプがついたところで、スコアを1プラスして、落下人の位置を管理している文字列から1文字削除して詰める。
と、思って作ってみたが、ループ処理の途中で文字列長が変わってしまうので、配列の添え字が範囲を超えてエラーになるのでこいつはだめだった。
代わりに、poke命令で半角スペースに置き換えて、ループを抜けた後に、strtrim命令で、半角スペースをトリム(取り除く)処理にした。
*fallmanmove ;落下人移動ルーチン fallmancnt = strlen(fmanpos) ;現在の落下人数 if gamecnt\g_speed=0 { ;g_speedの値フレームごとに1つ処理する if fallmancnt>0 { ;1人以上落下しているとき repeat fallmancnt pt=peek(fmanpos,cnt)-65 poke fmanpos,cnt,pt+66 pos fx(pt),fy(pt) gmode 2:celput 3,pt if pt=22 { ;ループ中に文字列長を変えてエラーにならないよう、スペースと置き換え poke fmanpos,cnt,32 poke fmancatch,cnt,32 ;スコア加算 score++ } loop if missflg=1 : return ;得点によって、最大落下人数を変更する maxfallman=1+(score>2)+(score>9)+(score>19)+(score>29)+(score>49)+(score>69)+(score>89)+(score>119) if fallmancnt < maxfallman { ;必ず1コマ以上間隔をあけて人を追加する if instr(fmanpos,0,"B") < 0 & (rnd(10) > 2) { fmanpos=fmanpos+"A" fmancatch=fmancatch+"0" } } ;得点した場合、スペースが文字列にあるので取り除く fmanpos = strtrim(fmanpos,3,32) fmancatch = strtrim(fmancatch,3,32) } else { ;単純に誰も表示されていなければ、一人追加 fmanpos=fmanpos+"A" fmancatch=fmancatch+"0" } } else { repeat fallmancnt pt=peek(fmanpos,cnt)-65 if pt >= 0 { ;スペースが含まれていた場合の対策 pos fx(pt),fy(pt) gmode 2:celput 3,pt } loop } return
こういう風に書くと簡単そうだが、いろいろ試行錯誤してたどり着いた。
実際に動かしたときに変数の内容がどうなっているかを確認する方法がログに出力するか、assert命令を書いて、デバッグウィンドウを表示して確認しなくてはならず、自分で考えた通りになっていない原因を探すのに苦労した。
そこは歴史の長いHSP。ちょっと検索すると、knowbugというツールがあった。
これを組み込むと、HSPでプログラムをステップ実行(1行ずつ実行)ができ、変数の内容も都度表示できる。
knowbugがなかったら、なかなか開発が進まなかっただろうなぁ。ありがたい。
そうして作成したのがこれ。
youtu.be
うん。なかなかそれっぽくなってきたよ。