みなさんこんにちは、最近は身体を酷使しすぎて疲れが抜けないSです。

今回はCF2.5でレーザーをつくったので忘れないようにいつものようにメモ記事にします。

レーザーをつくるのは意外と簡単で細長いオブジェクトを発射オブジェクトから発生させてやればそれだけでいけます。なんせ光の速さで発射されるのでいきなり画面端まで届いても全く違和感がありません。強いて言えば発射される前に光が集る様な発生モーションと終わったときに徐々に細くなって消えるモーションをいれてやれば完璧です。実際そういうゲームも多いです。

だがしかしっ

重金属ガールはシールドで防ぐんだよぉぉぉぉっ!!!

という訳で何かに遮られたときにそこで止まるレーザーを作りました。



2パターンあります。(動画はそのうちの超連射方式版です)

一つ目は金字塔と冥府の王で使った方法なのですが細長いレーザーの画像をX軸の方向のみスケールを変更して伸縮させてやる方法。
この方法の利点はあらゆる意味でお手軽ということ。
欠点は直線にしか発射させられないことと画像をアニメーションさせられないということ。

二つ目は小さい弾を切れ目なく連射して1本のレーザーに見せる方法。
この方法の利点は軌道を好きに変えられることと、見た目を自分の好きなようにできること。
欠点は制御があらゆる意味で難しいということ。

です。
今回もサンプルを置いておきますので見たい人はどうぞ。

ダウンロード

大まかな所はサンプルのイベントリストにコメントを入れているのでわかると思いますので今回の記事も補足説明に留まります。

今回はforeachループとそれを使ったオブジェクトの同期を理解していないと難しいと思います。

foreachループはアクションにあるカウントの中の「各オブジェクトにつき」というやつです。
これは高速ループとは違い文字通り「各オブジェクト」につき処理を行うということです。
もう少し詳しく説明すると同一のオブジェクトが複数あるときに一括処理ではなくオブジェクト一つ一つ個別に処理するということです。
この同一オブジェクトというのは複製で作ったオブジェクトのことでオブジェクト名も完全に同じものになります。クローンでつくったものはオブジェクト名の後に数字がついてオブジェクト2みたいになりますがこちらは別オブジェクトになるので気をつけてください。
通常、同一オブジェクトの処理は全て同じ処理をするか個別に処理するかをCF2.5側で勝手に判断して行っています。
例えば「障害物と衝突」という条件が入っていればその衝突したオブジェクトだけにアクションを適用してくれたり、「常に実行」の条件下で変数Aに1を追加とあれば存在する同一オブジェクト全ての変数Aに1が追加されたりします。
条件次第である程度バラバラにオブジェクトの処理をすることは可能なのですが意図した動作をしてくれないことがよくあります。特に同一オブジェクトの処理を同一時間(1フレーム内)で行うとよく変な動作になります。
そんなときforeachループを利用します。

で、今回は更にそのforeachで処理する各オブジェクトに別の各オブジェクトを同期して処理しています。

同一ではないオブジェクト同士を同期させるにはインビルドペアなどいくつか方法がありますが今回は固定値を利用した方法を採用しています。
オブジェクトにはそれぞれ個別の認識番号である固定値が設定されています。
親になるオブジェクトの固定値を子になるオブジェクトの変数に代入して固定値と変数が同じなら処理するというイベントを組めば別のオブジェクト同士を同期することができます。
この方法の利点はオブジェクトの作成されるタイミングも同期するオブジェクトの数も関係なく処理できることです。
例えば巨大なキャラに破壊できるパーツを5つ作って同期させてやることも簡単にできます。
全てのパーツオブジェクトの変数に巨大なキャラオブジェクトの固定値を入れてやって、条件に「巨大なキャラの固定値=パーツオブジェクトの変数」を入れてやればよいのです。

ただし巨大なキャラが複数体になったときにおかしな挙動になることがよくあるのでforeachと組み合わせるわけです。

各巨大なキャラにつき~
パーツオブジェクトの変数=巨大なキャラの固定値

みたいな感じですね。
変数を比較するときに基本的にはforeachを指定するオブジェクトは後ろにもってくるようにしてください。
条件で指定する場合どちらのオブジェクトを先にもってくるかでアクション時にピックアップされるオブジェクトが変わってくるためです。
あくまで自分の経験則によるものであってCF2.5がどういう風に判断しているのかが重要なので上手く動作しないときは逆にしてみるといいかもしれません。

このサンプルでは

親オブジェクト(発射台)の固定値
レーザー根本の識別番号

の2つで同期を取っています。

どの発射台(固定値)から発射されたレーザーで何番目(識別番号)に発射されたレーザーなのか、という認識です。

また小ネタとして
経過フレーム数 mod 2 を利用して

=0 偶数
=1 奇数

という条件もつかっています。

ではサンプルファイルの説明ですが

スケール変更方式はレーザー根本とレーザー本体とレーザー先端の3つのパーツで構成されています。
レーザー本体は細長い1枚の画像でこれのX軸のスケールを変更してレーザーを伸縮しています。
ホットスポットとアクションポイントを両端に持ってくることで拡縮しても根本と先端がきっちりと位置同期するようになっています。
計算しやすいように100ドットの長さで作成してあるので0.01単位で変化させれば1ドットづつの伸縮が可能となっています。
無限に伸ばすのもあれなので最長は表示領域の最大値640にしています。
スケールに換算すると6.40ですね。
障害物に当たったときは高速ループを利用して1フレームで障害物にギリギリ当たらない長さまで縮小しています。
こちらは比較的シンプルにできました。
そしておかしな挙動もないのでいろいろな場面で利用できます。

続いて超連射方式ですがこちらもレーザー根本とレーザー本体とレーザー先端の3つのパーツで構成されていますがレーザー本体にアニメーションが2パターンあります。
こちらは360度撃てるようにベクター動作で移動します。
その際、レーザーとレーザーが連なって見えるようにレーザーの長さ16ドットと同じか少し短い距離を移動するように速度を1550(いろいろ試した結果ベクター動作は速度100で1フレーム1ドットの移動になるようです)に設定しました。上下左右の4方向なら1600でも良いのですが中途半端な角度になると一部隙間が確認できたので少し短めの1550で設定しました。
レーザーをアニメーションーのパターンAとBが交互になるように発射します。
レーザー根本で1フレームごとに照射時間をカウントしておきその値が偶数か奇数かでアニメーションシーケンスを切り替えています。
発射された後はアニメーションのフレームはレーザー根本と同期させています。
レーザーの先端は最初の1発だけ発射してあとはそれを使いまわしています。
レーザー本体が障害物に当たらなかったときはそのまま画面外へ出ていき、画面外では絶対に利用しないであろう位置に強制移動して待機。
レーザー本体が障害物に当たったときは障害物に当たったレーザー本体の位置に移動します。同時にレーザー本体が破壊されるのであたかも障害物に当たってるかのようにみえるというカラクリです。

こちらは苦労してつくりましたがいろいろとつくりが甘く状況を考えて利用しないと行けないレベルの出来です。
具体的には
障害物に遮られた時に障害物より先のレーザーは破壊されないので飛んで行くのが見える。
まあ消滅するのもおかしな話なのでこれはこれでありなんだけど、そのとき障害物に遮られるレーザーが2つ以上存在することがあるのに対しレーザーの先端は1つしかないのでおかしなことになります。
レーザーを薙ぎ払うパターンにしたときに先端が明後日の方向に飛んでいったりもします。
もう少しいろいろと考える余地は残っているのですが重金属ガールで想定される使い方ではこれで問題ないのでこれで完成としています。
最終的には雷電IIのプラズマレーザーみたいなのがつくれたら良いな~とおもっていますが先は長い。

誰かこれ改造して作ったサンプルうpしてくれてもいいのよ|д゚)チラッ

という訳でいよいよ重金属ガールにも光学兵器が登場しますがこのサンプルを上手く移植できるでしょうか…心配です。

制作もゆったりとしたペースですが進んでいますのでのんびり完成を待っていてくださいね。

それでは今回はこの辺で!
アデュー(´・ω・`)ノシ