Unityで装備している武器をキー操作で切り替えられるようにする機能

前回までで、敵キャラ、主人公の双方の攻撃とダメージの機能が出来ました。

Unityで敵キャラが主人公に近づいた時に攻撃をしてくる機能を作成していきます。
Unityで主人公キャラが剣を振って敵キャラを攻撃出来るようにする機能を作成します

主人公キャラの武器はひとつで固定となっていますが、これを特定のキーを押したら武器を切り替えられるようにしてみます。

初期設定として懐中電灯を持つようにし、キーの1を押すと次の武器の剣に切り替えます。
さらにキーを押すと次の武器または持ち物に変更します。

今回はキーの1を押すごとに順番に武器を切り替える仕様にしています。

今回の機能を作成すると、

↑のように装備している武器を切り替える事が出来るようになります。

今回はとりあえず武器の切り替えを出来るという最低限の機能を追加します。

あらかじめ装備品をヒエラルキー上に置いておくパターンと装備品をプレハブ化し、その都度インスタンス化するパターンを作っていきます。

スポンサーリンク

武器をキャラクターに持たせる

Equip空オブジェクトの子要素に武器を移動

今まで懐中電灯や剣を右手の子要素として設置していましたが、右手の子要素にEquipという空のゲームオブジェクトを作り、そこに合うように懐中電灯と剣の位置、角度を合わせて配置します。

武器の合わせ方は

Unityでキャラクターの手の位置に正確に武器を持たせるように調整します。なんとなく持たせる位置を設定していた人には朗報かも!?

を参考にしてください。

空オブジェクトEquipは右手の子要素に配置

Equipは上のような感じで配置します。

キャラクターは物を持っているようにアニメーションさせていないので、だいたいの位置で合わせます。

物を持って歩いているアニメーションであればさらにわかりやすいと思います。

手等の一部を部分的にアニメーションさせたい場合は

体の一部分だけのアニメーションを変更したい場合はAnimatorControllerのレイヤーとアバターマスクを使う事で実現出来ます。

の記事を参考にしてください。

武器切り替えスクリプトChangeEquipを取りつける

Equipには新しいスクリプトChangeEquipを追加します。publicの値は後で設定します。

Equipは装備を配置する目印なのでMeshとコライダは無効にしておきます。
(間違って3DオブジェクトのCubeでやってしまったのでこうなっています)

ただの空オブジェクトを作成し位置を合わせるだけでOKです。その際Scaleの値は必ず1にしておいてください。

子のTransform(位置情報)は親の位置やScaleの相対値になっていく為、Equipの子要素にも影響が出てしまう為です。

武器を切り替えるスクリプトChageEquip

装備する武器はEquipの子要素に並べておき、インスペクタでweaponsに設定するようにします。

現在装備している武器はweapons配列の何番目かをequipmentで持つようにします。

Startメソッドでは主人公操作スクリプトのMoveと主人公のアニメーションイベント受け取りスクリプトのProcessMyAttackを取得します。

最初の武器のゲームオブジェクトをアクティブにします。

Updateメソッドでは1キーを押した時に主人公がノーマル状態の時だけ武器を変更出来るようにします。

Changeメソッドが実際に武器を切り替えている処理で、まずは配列要素番号を+1した後に、その武器のゲームオブジェクトをアクティブにし、他のゲームオブジェクトを非アクティブにしています。

装備を変えたらProcessMyAttackのSetColliderメソッドで武器のコライダも変更します。

ProcessMyAttackにSetColliderの追加と他のフィールド宣言等を変更します。

capColは元々CapsuleColliderで宣言していましたが、宣言部分でColliderに変更しておきます。

武器によってはCapsuleColliderではなくBoxCollider等を使う場合を考えてこうしておきます。

いわゆる多態性というやつでコライダは色々あるけどみんなコライダだという扱いをします。
太郎や花子など色々な人はいるけれどみんな人間という種族として取り扱うという事、

つまり、お前の物は俺の物、俺の物は俺の物というジャイアン的発想です(全然違う・・・)

これで二つの武器(というかひとつは懐中電灯ですが・・・)の切り替えが出来るようになりました。

スクリプトで武器をインスタンス化し装備させる方法もある

最初から武器を設定し非アクティブにしておくのではなく、プレハブのインスタンス化をしてEquipの場所に表示するという方法もあります。

これならばヒエラルキー上に武器が何十個も表示される事がなく、スクリプト上でインスタンス化し配置する事が出来ます。

Equipの子要素に配置した懐中電灯や剣をAssetsフォルダにドラッグ&ドロップしプレハブにします。

その後、剣等をキャラクターに正しく持たせたTransformのPosition、Rotation、Scaleの値をメモ帳等に書いておきます。

装備品のTransform情報をメモしておく

これは剣等のプレハブをインスタンス化した時に正確な位置や回転、サイズに合わせる為です。

これが終わったらヒエラルキー上のEquipの子要素の装備品は削除します。

ChangeEquipスクリプトを修正します。

まずはStartメソッドでequipmentに-1を入れます。

次にUpdateメソッドでChangeメソッドではなくInstantiateWeaponメソッドを呼び出すようにします。

最後に装備品をインスタンス化するInstantiateWeaponメソッドです。

今装備している武器があればその武器を削除し、インスペクタでweapons配列に先ほどプレハブ化した装備品をドラッグ&ドロップしておきます。

先ほどはヒエラルキーの装備品をインスペクタで設定しましたが、今回はプレハブ化した装備品を設定する必要があります。

武器をインスタンス化したらその武器のColliderコンポーネント(CapsuleColliderやBoxCollider等)をProcessMyAttackのSetColliderメソッドで設定します。

インスタンス化した武器の親要素はTransformのSetParentメソッドで自身(このスクリプトが設定されているゲームオブジェクト)であるEquipにします。

今回は懐中電灯と剣の2つの武器だけを設定したと想定していて、手動でそれぞれの位置や角度、サイズをインスタンス化した装備品に割り当てます。

ここで設定する数値は先ほどメモ帳に残したデータを記述します。

本来であれば武器のパラメータ等を保持するスクリプトを武器自体に設定しておき、そこからインスタンス化した時の位置や角度、サイズを設定するようにすればいいと思います。

今回は2つだけなので手動で設定しました。

ここら辺は

blenderで作成した服、鎧や足をガードする装備等を作成した後Unityに取り込み、キャラクターが装備を着せかえることが出来るようにします。

↑の服の着せ替えの記事でやっているのでそちらも参考にしてください。

装備を切り替える時に何も装備していない時はコライダの切り替えが出来ないので、ProcessMyAttackスクリプトを修正します。

1キーを押すとEquipの子要素の装備品が削除されたり、インスタンス化され表示されるようになりました。

武器切り替えをした時に武器をインスタンス化したサンプル

これで武器の切り替えが終了しました。

次回は敵に当たったエフェクトを設定してみます。

スポンサーリンク

記事をシェアして頂ける方はこちら

フォローして頂くとやる気が出ます

コメント

  1. マヴ より:

    はじめまして、かめくめちゃんさん
    いつもスクリプトを参考にさせてもらっています。
    ありがとうございます。

    ご質問なんですが
    ProcessmyAttackや、別のページにあったスクリプトのSetState
    など一部のメソッド(?)が認識してくれない状態です。
    エラーメッセージには
    error CS0246: The type or namespace name `ProcessMyAttack’ could not be found. Are you missing an assembly reference?
    のような感じで表示されました。
    使ったunityのバージョンは2017.3.1f1と5.6.2f1です。

    誠に忙しい中、申し訳ないのですが・・・
    同じようなエラーメッセージの方もいると思うので
    記事で回答か返答、よろしくお願いいたします。