• チュートリアル
  • 機能解説
  • リファレンス
  • 初代Altseedはコチラ

    • チュートリアル
    • 0章 : Altseedを初めよう
    • 1章 : ウィンドウを表示してみよう
    • 2章 : キャラクターを描画してみよう
    • 3章 : キャラクターに弾を撃たせてみよう
    • 4章 : クラスを自分で設計してみよう
    • 5章 : 敵・敵のショットを表示してみよう
    • 6章 : 当たり判定の機能を使ってみよう
    • 7章 : 音を鳴らしてみよう
    • 8章 : 得点を表示してみよう
    • 9章 : タイトル・ゲームオーバー画面を作ってみよう
    • 10章 : いざ、公開準備

    7章 : 音を鳴らしてみよう

    前章では、当たり判定を実装しました。
    この章では、ゲームに不可欠な音を追加します。
    ゲームには、オブジェクトの動きに合わせたサウンドエフェクト(SE)やゲームの雰囲気を作り出すBGMが必要です。
    以下では、SEやBGMを再生する処理を実装します。

    SEを鳴らす

    今回は、以下のSEを再生します。

    • プレイヤーのショット音
    • プレイヤーの死亡時サウンド
    • 敵共通の死亡時サウンド
    • まっすぐな弾を発射する敵のショット音
    • 放射ショットの敵のショット音

    プレイヤーのショット音を追加

    Player.csに以下のソースコードを追加します。

    using Altseed2;
    
    namespace Tutorial
    {
        // プレイヤーのクラス
        public class Player : CollidableObject
        {
    +       // ショット時の効果音
    +       private Sound shotSound;
    
            // コンストラクタ
            public Player(MainNode mainNode, Vector2F position) : base(mainNode, position)
            {
                // 衝突判定を行うように設定
                doSurvey = true;
    
                // テクスチャを読み込む
                Texture = Texture2D.LoadStrict("Resources/Player.png");
    
                // 中心座標を設定
                CenterPosition = ContentSize / 2;
    
                // コライダの半径を設定
                collider.Radius = Texture.Size.Y / 2;
    
    +           // ショット音を読み込む
    +           shotSound = Sound.LoadStrict("Resources/shot1.wav", true);
            }
    
            // 衝突時に実行
            protected override void OnCollision(CollidableObject obj)
            {
                // 衝突対象が敵か敵の弾だったら
                if (obj is Enemy || obj is EnemyBullet)
                {
                    // 自身を親から削除
                    Parent.RemoveChildNode(this);
                }
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // 移動を実行
                Move();
    
                // ショットを実行
                Shot();
    
                // CollidableObjectのOnupdate呼び出し
                base.OnUpdate();
            }
    
            // 移動を行う
            private void Move()
            {
                // 現在のX座標を取得する
                var x = Position.X;
                // 現在のY座標を取得する
                var y = Position.Y;
    
                // ↑キーでY座標を減少
                if (Engine.Keyboard.GetKeyState(Key.Up) == ButtonState.Hold)
                {
                    y -= 2.5f;
                }
    
                // ↓キーでY座標を増加
                if (Engine.Keyboard.GetKeyState(Key.Down) == ButtonState.Hold)
                {
                    y += 2.5f;
                }
    
                // →キーでX座標を増加
                if (Engine.Keyboard.GetKeyState(Key.Right) == ButtonState.Hold)
                {
                    x += 2.5f;
                }
    
                // ←キーでX座標を減少
                if (Engine.Keyboard.GetKeyState(Key.Left) == ButtonState.Hold)
                {
                    x -= 2.5f;
                }
    
                // テクスチャのサイズの半分を取得する
                var halfSize = Texture.Size / 2;
    
                // X座標が画面外に行かないように調整
                x = MathHelper.Clamp(x, Engine.WindowSize.X - halfSize.X, halfSize.X);
                // Y座標が画面外に行かないように調整
                y = MathHelper.Clamp(y, Engine.WindowSize.Y - halfSize.Y, halfSize.Y);
    
                // 調整された座標を設定
                Position = new Vector2F(x, y);
            }
    
            // ショット
            private void Shot()
            {
                // Zキーでショットを放つ
                if (Engine.Keyboard.GetKeyState(Key.Z) == ButtonState.Push)
                {
                    Parent.AddChildNode(new PlayerBullet(mainNode, Position));
    
    +               // ショット音を鳴らす
    +               Engine.Sound.Play(shotSound);
                }
            }
        }
    }
    
    // ショット時の効果音
    private Sound shotSound;
    

    Altseed2では、音源データをSoundクラスインスタンスに格納します。
    また、ファイルから音源データを読み込む場合は、以下のようにSound.LoadStrictメソッドを用います。

    // ショット音を読み込む
    shotSound = Sound.LoadStrict("Resources/shot1.wav", true);
    

    第一引数には、音源データファイルへのパスします。
    そして、第二引数には、音源データを事前に解凍するか否かを指定します。
    一般的に、短い音をたくさん鳴らすようなSEの場合は、事前に解凍します。
    一方、BGMのような長い音源に対しては、事前に解凍せず、逐次解凍するようにします。

    そして、読み込んだ音源データを再生するには、以下のようにEngine.Sound.Playメソッドを呼び出す必要があります。

    // ショット音を鳴らす
    Engine.Sound.Play(shotSound);
    

    引数として、上で作成したSoundクラスインスタンスを渡します。

    この段階でビルドし、実行するとZキーでショットを放った瞬間に音が鳴ると思います。

    プレイヤーの死亡時サウンドを追加

    ショット音と同様にPlayer.csに以下のソースコードを追加します。

    using Altseed2;
    
    namespace Tutorial
    {
        // プレイヤーのクラス
        public class Player : CollidableObject
        {
            // ショット時の効果音
            private Sound shotSound;
    
            // コンストラクタ
            public Player(MainNode mainNode, Vector2F position) : base(mainNode, position)
            {
                // 衝突判定を行うように設定
                doSurvey = true;
    
                // テクスチャを読み込む
                Texture = Texture2D.LoadStrict("Resources/Player.png");
    
                // 中心座標を設定
                CenterPosition = ContentSize / 2;
    
                // コライダの半径を設定
                collider.Radius = Texture.Size.Y / 2;
    
                // ショット音を読み込む
                shotSound = Sound.LoadStrict("Resources/shot1.wav", true);
            }
    
            // 衝突時に実行
            protected override void OnCollision(CollidableObject obj)
            {
                // 衝突対象が敵か敵の弾だったら
                if (obj is Enemy || obj is EnemyBullet)
                {
    +               // 死亡音を読み込む
    +               var deathSound = Sound.LoadStrict("Resources/Explosion.wav", true);
    +
    +               // 死亡音を再生
    +               Engine.Sound.Play(deathSound);
    +
                    // 自身を親から削除
                    Parent.RemoveChildNode(this);
                }
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // 移動を実行
                Move();
    
                // ショットを実行
                Shot();
    
                // CollidableObjectのOnupdate呼び出し
                base.OnUpdate();
            }
    
            // 移動を行う
            private void Move()
            {
                // 現在のX座標を取得する
                var x = Position.X;
                // 現在のY座標を取得する
                var y = Position.Y;
    
                // ↑キーでY座標を減少
                if (Engine.Keyboard.GetKeyState(Key.Up) == ButtonState.Hold)
                {
                    y -= 2.5f;
                }
    
                // ↓キーでY座標を増加
                if (Engine.Keyboard.GetKeyState(Key.Down) == ButtonState.Hold)
                {
                    y += 2.5f;
                }
    
                // →キーでX座標を増加
                if (Engine.Keyboard.GetKeyState(Key.Right) == ButtonState.Hold)
                {
                    x += 2.5f;
                }
    
                // ←キーでX座標を減少
                if (Engine.Keyboard.GetKeyState(Key.Left) == ButtonState.Hold)
                {
                    x -= 2.5f;
                }
    
                // テクスチャのサイズの半分を取得する
                var halfSize = Texture.Size / 2;
    
                // X座標が画面外に行かないように調整
                x = MathHelper.Clamp(x, Engine.WindowSize.X - halfSize.X, halfSize.X);
                // Y座標が画面外に行かないように調整
                y = MathHelper.Clamp(y, Engine.WindowSize.Y - halfSize.Y, halfSize.Y);
    
                // 調整された座標を設定
                Position = new Vector2F(x, y);
            }
    
            // ショット
            private void Shot()
            {
                // Zキーでショットを放つ
                if (Engine.Keyboard.GetKeyState(Key.Z) == ButtonState.Push)
                {
                    Parent.AddChildNode(new PlayerBullet(mainNode, Position));
    
                    // ショット音を鳴らす
                    Engine.Sound.Play(shotSound);
                }
            }
        }
    }
    

    敵共通の死亡時サウンドを追加

    すべての敵共通で再生するため、Enemy.csに以下のソースコードを追加します。

    using Altseed2;
    
    namespace Tutorial
    {
        // 敵の基礎となるクラス
        public class Enemy : CollidableObject
        {
            // 倒された時に加算されるスコアの値
            protected int score;
    
            // プレイヤーへの参照
            protected Player player;
    
            // コンストラクタ
            public Enemy(Player player, Vector2F position) : base(player.mainNode, position)
            {
                // 衝突判定を行うように設定
                doSurvey = true;
    
                // プレイヤーへの参照を設定
                this.player = player;
            }
    
            // 衝突時に実行
            protected override void OnCollision(CollidableObject obj)
            {
                // 衝突対象が自機弾だったら
                if (obj is PlayerBullet)
                {
                    // スコアを加算
                    mainNode.score += score;
    
                    // 死亡時エフェクトを再生
                    Parent.AddChildNode(new DeathEffect(Position));
    
                    // 自身を削除
                    Parent.RemoveChildNode(this);
    
    +               // 死亡時サウンドを読み込み
    +               var deathSound = Sound.LoadStrict("Resources/Explosion.wav", true);
    +
    +               // 死亡時サウンドを再生
    +               Engine.Sound.Play(deathSound);
                }
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // CollidableObjectのOnUpdateを実行
                base.OnUpdate();
    
                // 画面外に出たら自身を削除
                RemoveMyselfIfOutOfWindow();
            }
        }
    }
    

    まっすぐな弾を発射する敵のショット音を追加

    StraightShotEnemy.csに以下のソースコードを追加します。

    using Altseed2;
    using System;
    
    namespace Tutorial
    {
        // まっすぐな弾を発射する敵
        public class StraightShotEnemy : Enemy
        {
            // カウンタ
            private int count = 0;
    
    +       // ショット時の効果音
    +       private Sound shotSound;
    
            // コンストラクタ
            public StraightShotEnemy(Player player, Vector2F position) : base(player, position)
            {
                // テクスチャを読み込む
                Texture = Texture2D.LoadStrict("Resources/UFO.png");
    
                // 中心座標を設定
                CenterPosition = ContentSize / 2;
    
                // 半径を設定
                collider.Radius = Texture.Size.X / 2;
    
                // 倒された時に加算されるスコアを設定
                score = 20;
    
    +           // ショット時の効果音を読み込む
    +           shotSound = Sound.LoadStrict("Resources/shot2.wav", true);
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // カウントが150の倍数で実行
                if (count % 150 == 0)
                {
                    // プレイヤーに対するベクトルの単位ベクトルを取得
                    var velocity = (player.Position - Position).Normal;
                    // ベクトルの長さを調整(弾速になる)
                    velocity *= 5;
    
                    // 弾を追加
                    Shot(velocity);
                }
    
                // 座標を設定
                Position -= new Vector2F(MathF.Sin(MathHelper.DegreeToRadian(count)) * 3.0f, 0);
    
                // EnemyのOnUpdateを実行
                base.OnUpdate();
    
                // カウントを進める
                count++;
            }
    
            // 弾を撃つ
            private void Shot(Vector2F velocity)
            {
                // 敵弾を画面に追加
                Parent.AddChildNode(new EnemyBullet(mainNode, Position, velocity));
    
    +           // ショット音を再生
    +           Engine.Sound.Play(shotSound);
            }
        }
    }
    

    放射ショットの敵のショット音を追加

    RadialShotEnemy.csに以下のソースコードを追加します。

    using Altseed2;
    
    namespace Tutorial
    {
        // 放射ショットの敵
        public class RadialShotEnemy : Enemy
        {
            // カウンタ変数
            private int count = 0;
    
            // 撃ち出すショットの個数
            private int shotAmount;
    
    +       // ショット時の効果音
    +       private Sound shotSound;
    
            // フレーム毎の速度
            private Vector2F velocity;
    
            // コンストラクタ
            public RadialShotEnemy(Player player, Vector2F position, int shotAmount) : base(player, position)
            {
                // 撃ち出すショットの個数を設定
                this.shotAmount = shotAmount;
    
                // テクスチャを読み込む
                Texture = Texture2D.LoadStrict("Resources/UFO.png");
    
                // 中心座標を設定
                CenterPosition = ContentSize / 2;
    
                // 半径を設定
                collider.Radius = Texture.Size.X / 2;
    
                // スコアを設定
                score = 30;
    
    +           // ショット時の効果音を読み込む
    +           shotSound = Sound.LoadStrict("Resources/shot2.wav", true);
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // カウントが250の倍数だったら
                if (count % 250 == 0)
                {
                    // 計算用のローカル変数
                    var half = shotAmount / 2;
    
                    for (int i = 0; i < shotAmount; i++)
                    {
                        // 現時点の座標からプレイヤーに向かうベクトルの単位ベクトルを取得する
                        var vector = (player.Position - Position).Normal;
    
                        // ベクトルを速度分掛ける
                        vector *= 7.0f;
    
                        // ベクトルを傾ける
                        vector.Degree += 30 * (i - half);
    
                        // ショットを放つ
                        Shot(vector);
                    }
                }
    
                // カウント÷100の余りが0~49だったら
                if (count % 100 < 50)
                {
                    // カウント÷100の余りが0だったら
                    if (count % 100 == 0)
                    {
                        // 進むベクトルを設定
                        velocity = (player.Position - Position).Normal * 3.0f;
                    }
    
                    // 速度分ベクトルを設定
                    Position += velocity;
                }
    
                // EnemyクラスのOnUpdateを呼び出す
                base.OnUpdate();
    
                // カウントを進める
                count++;
            }
    
            // 弾を撃つ
            private void Shot(Vector2F velocity)
            {
                // 敵弾を画面に追加
                Parent.AddChildNode(new EnemyBullet(mainNode, Position, velocity));
    
    +           // ショット音を再生
    +           Engine.Sound.Play(shotSound);
            }
        }
    }
    

    以上を追加し、ビルドするとSEが適切なタイミングで再生されると思います。

    BGMを鳴らす

    次は、BGMを再生する処理を追加しましょう。

    メインステージのBGMであるため、MainNode.csに以下のソースコードを追加します。

    using Altseed2;
    using System.Collections.Generic;
    
    namespace Tutorial
    {
        // メインステージのクラス
        public class MainNode : Node
        {
            // カウンタ
            private int count = 0;
    
            // 敵を格納するキュー
            private Queue<Enemy> enemies = new Queue<Enemy>();
    
            // キャラクターを表示するノード
            private Node characterNode = new Node();
            
            // プレイヤーの参照
            private Player player;
    
            // エンジンに追加された時に実行
            protected override void OnAdded()
            {
                // キャラクターノードを追加
                AddChildNode(characterNode);
    
                // UIを表示するノード
                var uiNode = new Node();
    
                // UIノードを追加
                AddChildNode(uiNode);
    
                // 背景に使用するテクスチャ
                var backTexture = new SpriteNode();
                // 背景のテクスチャを読み込む
                backTexture.Texture = Texture2D.LoadStrict("Resources/Background.png");
                // 表示位置を奥に設定
                backTexture.ZOrder = -100;
    
                // 背景テクスチャを追加
                AddChildNode(backTexture);
    
                // プレイヤーを設定
                player = new Player(this, new Vector2F(100, 360));
    
                // キャラクターノードにプレイヤーを追加
                characterNode.AddChildNode(player);
    
                // ウェーブを初期化する
                InitWave();
    
    +           // BGMを初期化する
    +           InitBGM();
            }
    
            // エンジンから削除されたときに実行
            protected override void OnRemoved()
            {
                // 衝突判定を全てリセット
                CollidableObject.objects.Clear();
            }
    
    +       // BGMを初期化
    +       private void InitBGM()
    +       {
    +           // BGMを読み込む
    +           var bgm = Sound.LoadStrict("Resources/BGM.wav", false);
    +
    +           // BGMのプレイ開始
    +           Engine.Sound.Play(bgm);
    +       }
    
            // ウェーブの初期化
            private void InitWave()
            {
                // enemies.Enqueue~でウェーブに敵を追加
                // 追加した順番に敵が出現する
    
    
                enemies.Enqueue(new ChaseEnemy(player, new Vector2F(700, 160), 2.0f));
    
                enemies.Enqueue(new StraightShotEnemy(player, new Vector2F(600, 620)));
    
                enemies.Enqueue(new Meteor(player, new Vector2F(910, 400), new Vector2F(-4.0f, 0.0f)));
    
                enemies.Enqueue(new RadialShotEnemy(player, new Vector2F(400, 160), 3));
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // ステージの更新
                UpdateStage();
    
                // カウントを進める
                count++;
            }
    
            // 敵召還関連
            private void UpdateStage()
            {
                // カウントが100の倍数だったら
                if (count % 100 == 0)
                {
                    // 敵が残っていたら画面に追加
                    if (enemies.Count > 0)
                    {
                        characterNode.AddChildNode(enemies.Dequeue());
                    }
                }
            }
        }
    }
    

    BGMに関する初期化をするメソッドInitBGMを実装し、 メインステージが始まった時点で再生するため、OnAddedで呼び出します。

    BGMを再生する場合も、基本的はSEと変わらず、Soundクラスインスタンスを用います。
    しかし、このままではうまくいきません。
    今回、BGMを再生するために、以下の処理が必要となります。

    • ループ処理
    • 再生している音の制御(一時停止、終了)

    ループ処理

    InitBGMメソッドに以下の処理を追加しましょう。

    using Altseed2;
    using System.Collections.Generic;
    
    namespace Tutorial
    {
        // メインステージのクラス
        public class MainNode : Node
        {
            // カウンタ
            private int count = 0;
    
            // 敵を格納するキュー
            private Queue<Enemy> enemies = new Queue<Enemy>();
    
            // キャラクターを表示するノード
            private Node characterNode = new Node();
            
            // プレイヤーの参照
            private Player player;
    
            // エンジンに追加された時に実行
            protected override void OnAdded()
            {
                // キャラクターノードを追加
                AddChildNode(characterNode);
    
                // UIを表示するノード
                var uiNode = new Node();
    
                // UIノードを追加
                AddChildNode(uiNode);
    
                // 背景に使用するテクスチャ
                var backTexture = new SpriteNode();
                // 背景のテクスチャを読み込む
                backTexture.Texture = Texture2D.LoadStrict("Resources/Background.png");
                // 表示位置を奥に設定
                backTexture.ZOrder = -100;
    
                // 背景テクスチャを追加
                AddChildNode(backTexture);
    
                // プレイヤーを設定
                player = new Player(this, new Vector2F(100, 360));
    
                // キャラクターノードにプレイヤーを追加
                characterNode.AddChildNode(player);
    
                // ウェーブを初期化する
                InitWave();
    
                // BGMを初期化する
                InitBGM();
            }
    
            // エンジンから削除されたときに実行
            protected override void OnRemoved()
            {
                // 衝突判定を全てリセット
                CollidableObject.objects.Clear();
            }
    
            // BGMを初期化
            private void InitBGM()
            {
                // BGMを読み込む
                var bgm = Sound.LoadStrict("Resources/BGM.wav", false);
    
    +           // BGMをループするように設定
    +           bgm.IsLoopingMode = true;
    +
    +           // ループ開始位置を設定
    +           bgm.LoopStartingPoint = 11.33f;
    +
    +           // ループ終了位置を設定
    +           bgm.LoopEndPoint = 33.93f;
    
                // BGMのプレイ開始
                Engine.Sound.Play(bgm);
            }
    
            // ウェーブの初期化
            private void InitWave()
            {
                // enemies.Enqueue~でウェーブに敵を追加
                // 追加した順番に敵が出現する
    
    
                enemies.Enqueue(new ChaseEnemy(player, new Vector2F(700, 160), 2.0f));
    
                enemies.Enqueue(new StraightShotEnemy(player, new Vector2F(600, 620)));
    
                enemies.Enqueue(new Meteor(player, new Vector2F(910, 400), new Vector2F(-4.0f, 0.0f)));
    
                enemies.Enqueue(new RadialShotEnemy(player, new Vector2F(400, 160), 3));
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // ステージの更新
                UpdateStage();
    
                // カウントを進める
                count++;
            }
    
            // 敵召還関連
            private void UpdateStage()
            {
                // カウントが100の倍数だったら
                if (count % 100 == 0)
                {
                    // 敵が残っていたら画面に追加
                    if (enemies.Count > 0)
                    {
                        characterNode.AddChildNode(enemies.Dequeue());
                    }
                }
            }
        }
    }
    

    BGMをループさせるには、SoundクラスインスタンスのIsLoopingModeプロパティをtrueにします。
    そして、音源の任意の区間をループさせる場合、

    • SoundクラスインスタンスのLoopStartingPointプロパティで区間の始点
    • SoundクラスインスタンスのLoopEndPointプロパティで区間の終点

    を指定する必要があります。

    再生している音の制御(一時停止、終了)

    MainNode.csに以下のソースコードを変更します。

    using Altseed2;
    using System.Collections.Generic;
    
    namespace Tutorial
    {
        // メインステージのクラス
        public class MainNode : Node
        {
    +       // BGMのID
    +       private int? bgmID = null;
    +
            // カウンタ
            private int count = 0;
    
            // 敵を格納するキュー
            private Queue<Enemy> enemies = new Queue<Enemy>();
    
            // キャラクターを表示するノード
            private Node characterNode = new Node();
            
            // プレイヤーの参照
            private Player player;
    
            // エンジンに追加された時に実行
            protected override void OnAdded()
            {
                // キャラクターノードを追加
                AddChildNode(characterNode);
    
                // UIを表示するノード
                var uiNode = new Node();
    
                // UIノードを追加
                AddChildNode(uiNode);
    
                // 背景に使用するテクスチャ
                var backTexture = new SpriteNode();
                // 背景のテクスチャを読み込む
                backTexture.Texture = Texture2D.LoadStrict("Resources/Background.png");
                // 表示位置を奥に設定
                backTexture.ZOrder = -100;
    
                // 背景テクスチャを追加
                AddChildNode(backTexture);
    
                // プレイヤーを設定
                player = new Player(this, new Vector2F(100, 360));
    
                // キャラクターノードにプレイヤーを追加
                characterNode.AddChildNode(player);
    
                // ウェーブを初期化する
                InitWave();
    
                // BGMを初期化する
                InitBGM();
            }
    
            // エンジンから削除されたときに実行
            protected override void OnRemoved()
            {
                // 衝突判定を全てリセット
                CollidableObject.objects.Clear();
            }
    
            // BGMを初期化
            private void InitBGM()
            {
                // BGMを読み込む
                var bgm = Sound.LoadStrict("Resources/BGM.wav", false);
    
                // BGMをループするように設定
                bgm.IsLoopingMode = true;
    
                // ループ開始位置を設定
                bgm.LoopStartingPoint = 11.33f;
    
                // ループ終了位置を設定
                bgm.LoopEndPoint = 33.93f;
    
                // BGMのプレイ開始
    +           bgmID = Engine.Sound.Play(bgm);
    -           Engine.Sound.Play(bgm);
            }
    
            // ウェーブの初期化
            private void InitWave()
            {
                // enemies.Enqueue~でウェーブに敵を追加
                // 追加した順番に敵が出現する
    
    
                enemies.Enqueue(new ChaseEnemy(player, new Vector2F(700, 160), 2.0f));
    
                enemies.Enqueue(new StraightShotEnemy(player, new Vector2F(600, 620)));
    
                enemies.Enqueue(new Meteor(player, new Vector2F(910, 400), new Vector2F(-4.0f, 0.0f)));
    
                enemies.Enqueue(new RadialShotEnemy(player, new Vector2F(400, 160), 3));
            }
    
            // フレーム毎に実行
            protected override void OnUpdate()
            {
                // ステージの更新
                UpdateStage();
    
                // カウントを進める
                count++;
            }
    
            // 敵召還関連
            private void UpdateStage()
            {
                // カウントが100の倍数だったら
                if (count % 100 == 0)
                {
                    // 敵が残っていたら画面に追加
                    if (enemies.Count > 0)
                    {
                        characterNode.AddChildNode(enemies.Dequeue());
                    }
                }
            }
        }
    }
    

    再生している音は、Engine.Sound.Playメソッドの戻り値であるint型のIDによって、制御できます。
    今回は、BGMはずっと再生させておくため、制御はしませんが、 今後、BGMを制御する場合に備えて、MainNodeクラスのbgmIDフィールドに格納しておきましょう。

    以上を反映させて、ビルドを行うとBGMが再生されると思います。

    まとめ

    本章では、ゲームに音を加えることによって、よりゲームらしくなったかと思います。
    みなさんのゲームでも、どんどん効果音をつけていってください。

    次の章では、ゲーム性を高める上で重要な得点を表示させていきましょう。

    Copyright © 2020 Altseed .