コガネブログ

平日更新を目標に Unity や C#、Visual Studio、ReSharper などのゲーム開発アレコレを書いていきます

【Unity 入門】全方位シューティングを作る 第7回 弾の作成と発射

目次

前回のチュートリアル

はじめに

前回は、ゲームの見栄えを少し良くするために、背景がスクロールするようにしました
今回は、プレイヤーが弾を発射するようにしていきます

弾の配置

まず、弾をシーンに配置していきます

「space-shooter/shots」フォルダ内の「1」を、Hierarchy の欄にドラッグします

このままだと名前が分かりづらいため、
配置した「1」を選択して、名前を「Shot」に変更します

これで、弾の配置が完了しました

弾のプレハブ化

次は弾をプレハブ化していきます

プレイヤーや背景は、常にシーンに存在するオブジェクトですが、
弾は、プレイヤーが発射して始めてシーンに現れるオブジェクトです

このようなオブジェクトはプレハブ化して、
ゲーム中にたくさん複製できるようにしておきます

「Scripts」フォルダを作成したときと同様の手順で、
「Prefabs」フォルダを作成します

さらに、Hierarchy の欄の「Shot」オブジェクトを
「Prefabs」フォルダにドラッグします

これで、弾のプレハブが作成できました

シーンに存在する「Shot」オブジェクトは不要になるため、
Hierarchy で「Shot」オブジェクトを選択して、Delete キーを押して

削除します

これで、弾のプレハブ化が完了しました

弾を制御するスクリプトの作成

次は、弾の移動を行うスクリプトを作成していきます

「Player」スクリプトを作成した時と同様の手順で、
「Shot」スクリプトを作成します

そして、作成した「Shot」スクリプトをコードエディタで開き、
下記のコードを記述します

using UnityEngine;

// プレイヤーが発射する弾を制御するコンポーネント
public class Shot : MonoBehaviour
{
    private Vector3 m_velocity; // 速度

    // 毎フレーム呼び出される関数
    private void Update()
    {
        // 移動する
        transform.localPosition += m_velocity;
    }

    // 弾を発射する時に初期化するための関数
    public void Init( float angle, float speed )
    {
        // 弾の発射角度をベクトルに変換する
        var direction = Utils.GetDirection( angle );

        // 発射角度と速さから速度を求める
        m_velocity = direction * speed;

        // 弾が進行方向を向くようにする
        var angles = transform.localEulerAngles;
        angles.z = angle - 90;
        transform.localEulerAngles = angles;

        // 2 秒後に削除する
        Destroy( gameObject, 2 );
    }
}

さらに、「Utils」スクリプトもコードエディタで開き、
Utils クラスの末尾に下記のコードを記述します

// 指定された角度( 0 ~ 360 )をベクトルに変換して返す
public static Vector3 GetDirection( float angle )
{
    return new Vector3
    (
        Mathf.Cos( angle * Mathf.Deg2Rad ),
        Mathf.Sin( angle * Mathf.Deg2Rad ),
        0
    );
}

これで、弾の移動を行うスクリプトの用意ができたので、

Unity エディタに戻り、「Shot」スクリプトを
「Shot」プレハブにドラッグして設定します

「Shot」プレハブを選択して、Inspector の欄に
「Shot」スクリプトが表示されていれば、正常に反映できています

弾を発射するコードの作成

ここまでで、弾を発射するための準備ができたので、
プレイヤーが弾を発射するコードを作成していきます

「Player」スクリプトをコードエディタで開き、
m_speed 変数の下に下記のコードを記述します

public Shot m_shotPrefab; // 弾のプレハブ
public float m_shotSpeed; // 弾の移動の速さ
public float m_shotAngleRange; // 複数の弾を発射する時の角度
public float m_shotTimer; // 弾の発射タイミングを管理するタイマー
public int m_shotCount; // 弾の発射数
public float m_shotInterval; // 弾の発射間隔(秒)

次に、Update 関数の末尾に下記のコードを記述します

// 弾の発射タイミングを管理するタイマーを更新する
m_shotTimer += Time.deltaTime;

// まだ弾の発射タイミングではない場合は、ここで処理を終える
if ( m_shotTimer < m_shotInterval ) return;

// 弾の発射タイミングを管理するタイマーをリセットする
m_shotTimer = 0;

// 弾を発射する
ShootNWay( angle, m_shotAngleRange, m_shotSpeed, m_shotCount );

最後に Update 関数の下に下記のコードを記述します

// 弾を発射する関数
private void ShootNWay( 
    float angleBase, float angleRange, float speed, int count )
{
    var pos = transform.localPosition; // プレイヤーの位置
    var rot = transform.localRotation; // プレイヤーの向き

    // 弾を複数発射する場合
    if ( 1 < count )
    {
        // 発射する回数分ループする
        for ( int i = 0; i < count; ++i )
        {
            // 弾の発射角度を計算する
            var angle = angleBase + 
                angleRange * ( ( float )i / ( count - 1 ) - 0.5f );

            // 発射する弾を生成する
            var shot = Instantiate( m_shotPrefab, pos, rot );

            // 弾を発射する方向と速さを設定する
            shot.Init( angle, speed );
        }
    }
    // 弾を 1 つだけ発射する場合
    else if ( count == 1 )
    {
        // 発射する弾を生成する
        var shot = Instantiate( m_shotPrefab, pos, rot );

        // 弾を発射する方向と速さを設定する
        shot.Init( angleBase, speed );
    }
}

これで、プレイヤーが弾を発射するコードの作成が完了しました

弾の発射

最後に、プレイヤーが弾を発射するように、
Unity エディタ上で調整していきます

「Player」オブジェクトを選択した状態で、
「Shot」プレハブを「Shot Prefab」の欄にドラッグして設定します

そして、「Player」スクリプトの各種パラメータを設定していきます

項目 内容
Shot Speed 弾の移動の速さ 0.1
Shot Angle Range 複数の弾を発射する時の角度 20
Shot Timer 弾の発射タイミングを管理するタイマー 0
Shot Count 弾の発射数 3
Shot Interval 弾の発射間隔(秒) 0.3

これで、Unity を再生すると、プレイヤーが弾を発射するようになったことが確認できます

おまけ:弾の発射数や発射速度の調整

「Player」スクリプトのパラメータをこのように設定すると

このように弾を発射することもできます
パラメータを変更していろいろ試してみて頂ければと思います

おまけ:弾の画像の変更

「Shot」プレハブを選択した状態で
「space-shooter/shots」フォルダ内の好きな画像を
「Sprite」の欄にドラッグすることで、

発射する弾の画像を変更することができます
興味があれば、いろいろな画像に変更してみて頂ければと思います

次回は、敵を作成していきます

次のチュートリアル

チュートリアル一覧