ロゴ ロゴ

【Den3夏のゲームジャム】当たり判定を作った【ウディタ】

はじめに

夏合宿で熱海へ行き、そのとき部内GameJamで作ったものを紹介をします。
使用ソフトはウルフエディタ。
せっかくなので、それの備忘録も兼ねて書いていきます。

企画と内容

まずGameJamのテーマが「コレクション」ということで、何かを集める要素を入れようと考えました。
そこで、思い出したのが、某国の王子が町に落ちたものを塊で巻き込んでいくゲームです。
また、私の好きなゲームジャンルがドット絵横スクロール2dアクションということもあり、それっぽいアクションゲームを作ることが目標です。
今回作りたかったのが、横スクロール2dアクションで、制限時間内になるべく多くアイテムを集めるというゲーム。
制作にかかった時間は1~2週間程度。
ただ、完成せず…
ウディタで2dアクションを作る難易度が高く、初ウディタでやるものではない気がします。
途中までですが、よかったら見ていってください。

ゲーム紹介

開発画面とアイテムを取得したときの様子です。


テストプレイで動かしてみます。
プレイヤーを移動して右にある赤い実をに近づくと、赤い実は消えスコアという共有変数が+1されました。
どっちかといえば塊魂よりスーパーマリオですね、コレ。

作ったコモン

今回作成したのは触れるとスコア加算されて消滅するアイテムです。
イベントを作り、イベントにアイテムの見た目を貼り付けます。
イベントの数が多いので、全てのイベントに同じコモンを与えて、イベントでコモンを呼び出す形にしました。
コモンの中身とセルフ変数は以下になります。

■変数操作: CSelf29[PL_W] = 32 - 0 
■変数操作: CSelf30[PL_H] = 32 - 0 
■変数操作+: CSelf23[EV_TX] = 呼出マップイベント の 画面X座標(キャラ中央)
■変数操作+: CSelf24[EV_TY] = 呼出マップイベント の 画面Y座標(足下)
■変数操作: V8[PL_Hプレイヤー当たり高さ] = CSelf23[EV_TX] + 0 
■変数操作: CSelf25[EV_mapX] = CSelf23[EV_TX] + 16 
■変数操作: CSelf26[EV_mapY] = CSelf24[EV_TY] + 16 
■変数操作: CSelf12[PL_CX] = V5[PL_Xプレイヤーマップx座標] - 0 
■変数操作: CSelf13[PL_CY] = V6[PL_Yプレイヤーマップy座標] - 0 
■変数操作: CSelf13[PL_CY] += 5 + 0 
■条件分岐(数値):  【1】 CSelf2[当たり幅]  が   0 と同じ 
-◇分岐: 【1】  [ CSelf2[当たり幅]  が  0 と同じ  ]の場合↓
 |■変数操作: CSelf14[IT_W] = 32 - 0 
 |■
-◇上記以外
 |■変数操作: CSelf14[IT_W] = CSelf2[当たり幅] - 0 
 |■
◇分岐終了◇
■条件分岐(数値):  【1】 CSelf3[当たり高さ]  が   0 と同じ 
-◇分岐: 【1】  [ CSelf3[当たり高さ]  が  0 と同じ  ]の場合↓
 |■変数操作: CSelf15[IT_H] = 32 - 0 
 |■
-◇上記以外
 |■変数操作: CSelf15[IT_H] = CSelf3[当たり高さ] - 0 
 |■
◇分岐終了◇
■条件分岐(数値):  【1】 CSelf29[PL_W]  が   0 と同じ 
-◇分岐: 【1】  [ CSelf29[PL_W]  が  0 と同じ  ]の場合↓
 |■変数操作: CSelf29[PL_W] = 32 - 0 
 |■
◇分岐終了◇
■条件分岐(数値):  【1】 CSelf30[PL_H]  が   0 と同じ 
-◇分岐: 【1】  [ CSelf30[PL_H]  が  0 と同じ  ]の場合↓
 |■変数操作: CSelf30[PL_H] = 32 - 0 
 |■
◇分岐終了◇
■変数操作: CSelf16[DX] 絶対値= CSelf12[PL_CX] - CSelf25[EV_mapX] 
■変数操作: CSelf17[DY] 絶対値= CSelf13[PL_CY] - CSelf26[EV_mapY] 
■変数操作: CSelf16[DX] = CSelf16[DX] * CSelf16[DX] 
■変数操作: CSelf17[DY] = CSelf17[DY] * CSelf17[DY] 
■変数操作: CSelf18[D2] = CSelf16[DX] + CSelf17[DY] 
■変数操作: CSelf19[PW] = CSelf29[PL_W] + 0 
■条件分岐(数値):  【1】 CSelf30[PL_H]  が   CSelf19[PW] 未満 
-◇分岐: 【1】  [ CSelf30[PL_H]  が  CSelf19[PW] 未満  ]の場合↓
 |■変数操作: CSelf19[PW] = CSelf30[PL_H] + 0 
 |■
◇分岐終了◇
■変数操作: CSelf20[IW] = CSelf14[IT_W] + 0 
■条件分岐(数値):  【1】 CSelf15[IT_H]  が   CSelf20[IW] 未満 
-◇分岐: 【1】  [ CSelf15[IT_H]  が  CSelf20[IW] 未満  ]の場合↓
 |■変数操作: CSelf20[IW] = CSelf15[IT_H] + 0 
 |■
◇分岐終了◇
■変数操作: CSelf21[RAD] = CSelf19[PW] / 2 
■変数操作: CSelf21[RAD] += CSelf20[IW] / 2 
■変数操作: CSelf22[RAD2] = CSelf21[RAD] * CSelf21[RAD] 
■条件分岐(数値):  【1】 CSelf18[D2]  が   CSelf22[RAD2] 未満 
-◇分岐: 【1】  [ CSelf18[D2]  が  CSelf22[RAD2] 未満  ]の場合↓
 |■条件分岐(数値):  【1】 CSelf1[加点]  が   0 と同じ 
 |-◇分岐: 【1】  [ CSelf1[加点]  が  0 と同じ  ]の場合↓
 | |■変数操作: V25[SCORE] += 1 + 0 
 | |■
 |-◇上記以外
 | |■変数操作: V25[SCORE] += CSelf1[加点] + 0 
 | |■
 |◇分岐終了◇
 |■
◇分岐終了◇
■


イベントは大きさを変えても対応できるように条件分けし、プレイヤーとイベントの位置を読み取っています。
当たり判定の計算では、プレイヤーとイベントの幅高さを考慮して一番プレイヤーとイベントの距離が近くなるときの長さの2乗より、プレイヤーとイベントとの中心の距離の2乗が小さいかどうかを連続して調べています。
2乗なのは、x軸の距離の2乗とy軸の距離の2乗を足していて、直角三角形の斜辺の2乗を距離として扱っているから(平方根の計算は重いのでカット)です。
もし条件を満たしたら、スコアという変数をプラス1して終わらせます。
このときコモン内でイベントの一時消去をすると、コモンイベントのみが消えてマップイベントのループは消えません。

イベントの配置

イベントの中身としては、マップを開いたときにコモンを呼び出しループさせ、コモンが条件を満たしたら勝手に消滅する仕組みです。
イベントの中身↓

■ループ開始
 |■変数操作: このEvのSelf0 = V25[SCORE] + 0 
 |■イベントの挿入[名]: ["アイテム取得"] <コモンEv 246>  / 0 / 0 / 0 / 0
 |■条件分岐(数値):  【1】 V25[SCORE]  が   このEvのSelf0 以外 
 |-◇分岐: 【1】  [ V25[SCORE]  が  このEvのSelf0 以外  ]の場合↓
 | |■イベントの一時消去:このEv (0フレーム)
 | |■
 |◇分岐終了◇
 |■ウェイト:1 フレーム
 |■
◇ループここまで◇◇
■


コモンの呼び出し前後でスコアの値が変化していないか調べ、変化していたらイベントを消去してループを終わります。
これをコピペで全てのイベント分用意します。
引数を使っているため、イベントごとにアイテムの幅や高さ、スコア加算点を調整することができます。
画像のようなデフォルト状態で、点数1点・幅高さはマップ1マス分となっています。
これでアイテム取得について実装できました。

苦戦した要素とか

今回詰まったところが、当たり判定です。
ウディタ公式サイトに、「アクションゲームシステム改」という配布コモンがありますので、これを使うと簡単に2dスクロールが実現できます。
アイテム取得要素を入れたかったので、それについては前述のように自作してみたのですが、これが難しかったです。
ウディタにはデフォルトで、プレイヤーと接触したらイベントが発動する仕組みがありますが、私がやってみても動きませんでした。
AGS改を入れているから位置情報がずれるのかな?検証はしてませんが、それが原因な気がします。
AIに聞いたところ、マップからプレイヤーの位置情報を取得し続けて、イベントの画面上の位置と一致したときにイベントを発動させる仕組みにすればいいとのことでした。
ここで、新しいコモンを作らないといけないことになりました。
イメージですが、イベントがコマンドラインを打つことだとすると、コモンはコマンドの作成って感じです。
位置情報についてですが、位置を取得したとして、それがプレイ画面の位置なのかマップに基づく位置なのかで、それの補正などをしないといけないっぽいです。
そうなんだーたしかにunityにもキャンバスっていうのあったなーと思ったり(1詰まり)。
もしゲームにする余裕が生まれたら、時間制限やスコア発表の画面、一定のスコア以上で体が大きくなる要素など作りたいです。

ウルフエディタ

初めてのウディタということで、インストールから使えるまで整えていきます。
詳しいものは、いろんなネット記事で確認できます。
あまり頭を使いたくなかったので、コモンの部分はほぼAIに考えさせました。
それを考えるのがGameJamな気もしますが、やりたくなかったのです。
ほどほどに嘘も混じっているので、コモン書かせるまではできなかったです…

インストール〜起動

まずウディタ公式サイトへ飛び、パッケージをダウンロードします。
解凍したらフォルダの中身はこうなります(Windows)。

ウディタではこのフォルダが1つのゲームになるので、元フォルダとしてコピーして別に置いておくといいかも。
ここのDataというフォルダですが、全てをゲームで使うわけではないので、フォルダを作って(名前をサンプルデータに変えて)、こっちに移しておきます。
Editorを起動して、ゲーム制作画面を開きます。
素材を自分で用意することもできるのですが、デフォルトで用意された素材を使いたいとき、上の四角をクリックすると最低限の素材が用意されたDataフォルダを再度作ってくれます。
サンプルデータに移した素材が使いたいときは、ファイルをDataフォルダにコピーして移せば使えます。

マップ作り〜テストプレイ

エディタを開いて、あらかじめ用意された設定を初期化していきます。
ーー
ゲーム画面になるマップを作りたいので、画面左上の白紙のアイコンをクリックします。
マップのサイズや名前、使用するマップチップなどを選択できます。
ーー
これで作成すると、ベースができます。
ここにマップチップを配置すると、作りたい世界を作ることができます。
今度はイベントのアイコンをクリックしてから、マップでプレイヤーの初期位置を決めて右クリックします。
出てきたリストのーを選択すると、プレイヤーの初期位置を設定できます。
一度テストプレイしてみます。
画面右上の緑の矢印をクリックして、テストプレイの画面を出します。
緑の矢印の左側のアイコンは、選択しておくとバグなど報告するデバッグのウィンドウも開けます。
操作して満足したら、ウィンドウを閉じればテストプレイを終了できます。

操作方法

筆者が調べた範囲で仕様などを書いています。
正しい情報は公式の説明書を参考にしてください。
– アクションゲームシステム改
ウディタ公式サイトに載っている配布コモンです。
入れると2dスクロールが簡単に実装できます。
配布場所はアクションゲームシステム改
使い方は、説明動画を出してくれている人がいるので、それを見ました。

  • 共通変数
    コモンやイベントで共通して使える変数。
    変数を増やすには、システムデータベース→タイプ→14:通常変数名→データ→データ数の設定から。
    ID欄や、イベントコマンド入力の3:変数操作のところから名前変更可能。
    もしコモンを外部から導入したら、共通変数が使われていないか確認。
    例えばAGS改では、V0[]、V1[]、V17[]の共通変数が使われていて(私調べ)、もし自作のイベントやコモンで同じ共通変数をいじると、動作しないことがあるので注意。

  • コモン変数
    共通変数は各イベントやコモンで共通して使われる変数ですが、コモン変数は呼び出されたイベントごとに使われる変数で、値は共有されません。
    今回のような、アイテムごとにコモンが使用されるような場合は、計算に使う変数をコモン変数にしておく必要があります(1詰まり)。
    コモンエディタ右上のーや、イベントコマンド入力の3:変数操作から名前変更可能。

  • マップチップの置き方
    デフォルトでレイヤーが3つ設定されていて、1は地面や建物の枠、2は道端の木や装飾品、3はテーブルの上の小物などで使用するイメージ。どこかのレイヤーをクリックするとマップチップが現れるので、使いたいチップを選択して、鉛筆ツールや長方形選択ツールなどでマップに配置していきます。

  • イベント起動条件
    イベントの起動条件は5つあり、ーのタブから選ぶことができます。
    ほぼ使い方としては名前の通りなので、自動実行と並列実行にだけ補足を入れます。
    自動実行はそのイベントが完了しない限り、イベントウィンドウでその下に作ったイベントが実行しない仕様です。
    並列実行は他のイベントが完了していようがいまいが自動で実行されます。

  • スクリーンショット
    テストプレイでゲーム画面をスクリーンショット撮ると、png画像がフォルダの中に保存されます。

おわりに

ウディタで作りたい部分をなんとか作り終えられて、GameJamに参加してよかったと達成感を覚えています。
ウディタ初めて触るのに2dスクロールを作ろうとしたのは失敗だった気もします。
GameJam +ブログというバフによって、なんとか挫折せず作れました。
やはり〆切、〆切は全てを解決する…!
そして、合宿やブログ企画に参加してくれたみなさん、ありがとうございました。
特にブログの方は思い付きで予告なく始めてしまったのに、付き合ってくれて感謝です。
この記事が誰かのウディタ挑戦のきっかけになれば嬉しいです。

コメント入力

関連サイト