@chocoshado

Are you sure you want to delete the question?

Leaving a resolved question undeleted may help others!

AudioSource.PlayOneShot()が動いているのに音が聞こえない

解決したいこと

ここに解決したい内容を記載してください。

こんにちは
現在Unityで効果音を再生しようとしているのですが、うまくいきません。
本を参考にしながら自分でコードを書いて動かしました。
本に書いてあったソースコードをそのまま実行するとちゃんと再生されました。
ソースコードの34~36,48~49行目が思い通りに動かず、ゲームクリアとゲームオーバーの音が全く聞こえません。
ゲーム開始時にBGMを再生しているため、ゲームクリアかゲームオーバーになった時にはsoundPlayer.Stop()でBGMを止め、soundPlayer.PlayOneShot()でそれぞれの効果音を再生するようにしています。
エラーメッセージはなく、soundPlayer.PlayOneShot()の処理は動いているようでした。

発生している問題・エラー

(エラーメッセージはなし)

該当するソースコード

using UnityEngine;
using UnityEngine.UI;

public class GameController : MonoBehaviour
{
    public GameObject mainImage;
    public Sprite gameClear;
    public Sprite gameOver;
    public AudioClip musicgameOver;
    public AudioClip musicgameClear;
    float time;
    // Start is called once before the first execution of Update after the MonoBehaviour is created
    void Start()
    {
        mainImage.SetActive(false);
    }

    // Update is called once per frame
    void Update()
    {
        // 車オブジェクトのtimeを取得し、条件に応じて画像を表示させる
        GameObject car = GameObject.FindGameObjectWithTag("Dead");
        CarController carCnt = car.GetComponent<CarController>();
        time = carCnt.time;

        // プレイヤーオブジェクトのisSafeを取得し、クリアか残念かを判定
        GameObject player = GameObject.FindGameObjectWithTag("Player");
        PlayerController playerCnt = player.GetComponent<PlayerController>();
        Debug.Log(time);
        // 4秒経ってプレイヤーが無事の時、クリア
        if (time > 4 && playerCnt.isSafe)
        {
            //↓ここがうまくいかない↓
            AudioSource soundPlayer = GetComponent<AudioSource>();
            soundPlayer.Stop();
            soundPlayer.PlayOneShot(musicgameClear);
            //↑ここがうまくいかない↑
            ActiveImage();
        }
        // 車に飛ばされたらゲームオーバー
        else if (playerCnt.isSafe == false)
        {
                //↓ここがうまくいかない↓
                AudioSource soundPlayer = GetComponent<AudioSource>();
                soundPlayer.Stop();
                soundPlayer.PlayOneShot(musicgameOver);
                //↑ここがうまくいかない↑

                mainImage.GetComponent<Image>().sprite = gameOver;
                ActiveImage();
        }
    }

    void ActiveImage()
    {
        mainImage.SetActive(true);
    }
}

自分で試したこと

①soundPlayer.Stop()をコメントアウト⇒BGMと効果音が同時に聞こえるが、効果音がほとんど雑音になっている
②soundPlayer.Stop()のコメントアウトを外して実行⇒BGMは問題なく聞こえるが、効果音はやはり聞こえない
③MainCameraオブジェクトのAudioListenerコンポーネントにチェックが入っているか確認⇒チェックは入っていた
④Gameウィンドウのスピーカーが有効か確認⇒有効になっていた

0 likes

2Answer

最近Unityでサウンド周りは触っていないのですが、もう一つ AudioSource がアタッチされたGameObjectを作って、 PlayOneShot はそちらで鳴らすようにしてみてはいかがですか。

0Like

Comments

  1. @chocoshado

    Questioner

    別オブジェクトにもAudioSourceをアタッチしてサウンド再生を切り替えるようにしたらうまくいきました!ありがとうございました!

私は Unity は触ったことがありません。
が、ゲーム制作は長年やっていました。

音楽を流しながら、効果音って鳴るものなんですが、すべて音楽として同時に鳴らさない。という、仕様に "した" のですか?

それはともかく…。
音楽を鳴らす前に、何か鳴っているか確認。鳴っていたら止めて、鳴らしたい音楽を鳴らす処理が必要です。鳴っていなかったら止める必要はないのだから。

あと、update だと、フレームごとに処理が来ますよね。
update って、描画で呼ばれると思うんです。
そこでは、描画だけで、他の処理は入れません。
如何に速く処理を終わらせるか。そういう場所です。
だからシンプルに書く。
ごちゃごちゃ書くところではありません。

ゲームの終了を判定するトリガーですよね。
だから、そこで Event を発生させて、その先で処理すると思います。

余談
update で 待機処理とかありえません。

余談2
神視点だから駄目。
自動車の場合、エンジンはタイヤの事なんか知りません。
空気圧がどうとか、ホイールだどうだとか。
でも、神視点だと一緒に考えちゃいます。
それを捨てて、タイヤはタイヤの責務を果たす。
エンジンはエンジンの責務を果たす。
オブジェクトは他のオブジェクトに関係なく、自分の責務を果たす。
って、考えないと厳しいかなぁと思います。
これは、ゲームバランスにも当てはまることです。
神さまなら何をやってもいいのか?

おまけ
日本人が書いたプログラミングの参考書は捨ててください。
儲けようとして出版しているだけだから、ろくなものがない。
海外の翻訳されている日本語訳と原著を、二冊買うと幸せになれますよ。

おまけ2
Unity はゲームを作れる人が、楽をするために使うもの。
楽というか、工程を減らすために。
なので、ゲームを作った事が無い人が使うものではない。
と、私は思っています。

0Like

Comments

  1. @chocoshado

    Questioner

    完全に本を鵜呑みにしていました💦
    BGMとゲームオーバー効果音の切り替えは同じUpdateメソッドでやるものだと思い込んでいました。Updateメソッドはゴチャゴチャ書くところではないのですね、一つ学びました!ありがとうございます。

  2. update って、描画で呼ばれると思うんです。
    そこでは、描画だけで、他の処理は入れません。

    Unityのプログラミングとしては間違っています。

    上記に書かれている図のように、Unityではゲームの制御処理を行うGameLogic(Updateメソッドもここから呼ばれる)と、描画処理を行うSceneRenderingからEndOfFrameまでの処理は、きっちりと区別されています。
    AudioSource.Stop のようなメソッドも、Updateも含めGameLogicのタイミングで行うのが一般的です。

    音楽を鳴らす前に、何か鳴っているか確認。鳴っていたら止めて、鳴らしたい音楽を鳴らす処理が必要です。鳴っていなかったら止める必要はないのだから。

    そのようなことも考えなくてもいいようですよ。
    そういった意味で「楽をするために使うもの」はうなずけますが、その代わり、昔に比べるとネットワークだったり、それ以上にやることも増えてますから、果たして楽になっているのやらどうか…。

  3. ありがとうございます。
    そういった、個別のゲームエンジンのアーキテクチャやシステムを覚える必要がありますね。

    そういった意味で「楽をするために使うもの」はうなずけますが、その代わり、昔に比べるとネットワークだったり、それ以上にやることも増えてますから、果たして楽になっているのやらどうか…。

    マルチプラットフォーム対応もそうですね。 Android は動くけど iPhone では動かないとか。

    納期一か月切っているのに、ちゃぶ台をひっくりかえすのは、今も昔も変わらない。
    とりあえず動くものを作っていると、最後が悲惨な状態になる。
    それならば Unity を使わないって、私はなっちゃいます。
    Lock-in されたくはないし、フルスクラッチで作ったほうがおもしろいから。

Your answer might help someone💌