0

Can you please help me with this problem, I'm adding FMOD to UNITY and want to change my music when Player gets damage, from FMOD side is OK, but in Unity it gives me an error: NullReferenceException: Object reference not set to an instance of an object MusicControl.Update () (at Assets/MusicControl.cs:

using UnityEngine;
using System.Collections;
using UnityEngine.SceneManagement;
using FMOD.Studio;

public class MusicControl : MonoBehaviour {


    [FMODUnity.EventRef]
    public string explosion = "event:/EXPLOSION";
    [FMODUnity.EventRef]
    public string shoot = "event:/SHOOT SOUND";
    [FMODUnity.EventRef]
    public string menuMusic = "event:/MENU MUSIC";

    int val;

    public FMOD.Studio.EventInstance musicEv;
    public FMOD.Studio.ParameterInstance musicPar;

    void Start()
    {
    }

    //music for menu, I'm call this function when my stage starts(menu game)
    public void MenuMusic()
    {
        musicEv = FMODUnity.RuntimeManager.CreateInstance(menuMusic);
        musicEv.start();
    }

    //music for level 1, I'm call this function when my stage starts(level game)
    public void LevelMusic() 
    {
        musicEv = FMODUnity.RuntimeManager.CreateInstance(menuMusic);
        musicEv.setParameterValue("FIGHT MUSIC", 100f);
        musicEv.getParameter("HEALTH", out musicPar);
        musicPar.setValue(100); 

        musicEv.start();
    }

    //I'm call this function when stages is close up
    public void StopMusic()
    {
        musicEv.stop(FMOD.Studio.STOP_MODE.IMMEDIATE);
    }

    // I'm take current Health from Player script
    void Update()

        val = GameObject.Find("Player").GetComponent<Player>().stats.curHealth;

        musicPar.setValue(val); //Unity gives me an error - NullReferenceException: Object reference not set to an instance of an object MusicControl.Update () (at Assets/MusicControl.cs:147)
    }

}

Thanks for advance

Thili77
  • 1,061
  • 12
  • 20
YellowJazz
  • 15
  • 1
  • 6
  • It is not good to put GameObject.Find() in Update(), because unity will find the object in the scene every frame, let say you have 100 object then unity need to find object named Player in every frame. Put it in Awake() function. – Tengku Fathullah Jan 06 '17 at 12:49

1 Answers1

0

The musicEv and musicPar variables are declared but never initialized before use in the Update() function.

You tried to to initialize them in the MenuMusic() and LevelMusic() functions but there is no guarantee that these functions will be called before the Update() function where you actually use them.

Remove musicEv = FMODUnity.RuntimeManager.CreateInstance(menuMusic); from both MenuMusic() and LevelMusic() functions and move it to the Start() or Awake() function in order to initialize musicEv.

After that, you can then initialize musicPar by calling musicEv.getParameter("HEALTH", out musicPar);.

Also, don't do val = GameObject.Find("Player") in the Update function. Do it once in Start() or Awake() function then save it to a global variable. In fact, it would be good to just cache the Player script that is attached to it.

public class MusicControl : MonoBehaviour {


    [FMODUnity.EventRef]
    public string explosion = "event:/EXPLOSION";
    [FMODUnity.EventRef]
    public string shoot = "event:/SHOOT SOUND";
    [FMODUnity.EventRef]
    public string menuMusic = "event:/MENU MUSIC";

    int val;

    public FMOD.Studio.EventInstance musicEv;
    public FMOD.Studio.ParameterInstance musicPar;

    private Player player;

    void Awake()
    {
        //Initialize musicEv
        musicEv = FMODUnity.RuntimeManager.CreateInstance(menuMusic);
        //Initialize musicPar(done with the out keyword)
        musicEv.getParameter("HEALTH", out musicPar);

        //Initialize player
        player = GameObject.Find("Player").GetComponent<Player>();
    }

    //music for menu, I'm call this function when my stage starts(menu game)
    public void MenuMusic()
    {
        musicEv.start();
    }

    //music for level 1, I'm call this function when my stage starts(level game)
    public void LevelMusic() 
    {
        musicEv.setParameterValue("FIGHT MUSIC", 100f);
        musicEv.getParameter("HEALTH", out musicPar);
        musicPar.setValue(100); 

        musicEv.start();
    }

    //I'm call this function when stages is close up
    public void StopMusic()
    {
        musicEv.stop(FMOD.Studio.STOP_MODE.IMMEDIATE);
    }

    // I'm take current Health from Player script
    void Update()
    {
        val = player.stats.curHealth;
        musicPar.setValue(val);
    }
}
Programmer
  • 121,791
  • 22
  • 236
  • 328
  • Many thanks Programmer But error still appears =(( I have Menu Manger script which control buttons on Menu Level and in this script I call MenuMusic() function but it gives me an error script: `public class MenuManager : MonoBehaviour { public MusicControl musicSystem; void Start() { musicSystem.MenuMusic(); }` and error: _NullReferenceException: Object reference not set to an instance of an object MusicControl.MenuMusic () (at Assets/MusicControl.cs:33) MenuManager.Start () (at Assets/Scripts/MenuManager.cs:28)_ – YellowJazz Jan 09 '17 at 04:40
  • But, now this is a different question on another script. Can you accept this once, then create a new question. Include that code in your new question and explain the where the problem is happening. I will take a look. – Programmer Jan 09 '17 at 10:47