Having a very strange problem passing a variable from one script to another

Hey Guys,

I have two C# scripts, InstanceTest.cs and TargetScript.cs, which are both attached to the same gameobject, TestManager.

In InstanceTest, I created a handle to TargetScript. In TargetScript, I have a public int called testVariable. The issue I am having is when I try to display the value of testVariable from the InstanceTest script.

It works fine in the Start function, but in the Update function, I keep getting a nullReferenceException error.

I can’t for the life of me figure out why it is working in one function and not the other. Once I create the handle, I should have continuing access.

Here are the two scripts:

using UnityEngine;
using System.Collections;

public class InstanceTest : MonoBehaviour {

    public TargetScript ref_TargetScript;
 
    void Start()
    {
        // get access to the TargetScript script on the same gameobject
        TargetScript ref_TargetScript = GetComponent<TargetScript>();

        Debug.Log(ref_TargetScript.testVariable);
    }

    void Update()
    {
        Debug.Log(ref_TargetScript.testVariable);
    }
}

and

using UnityEngine;
using System.Collections;

public class TargetScript : MonoBehaviour {

    public int testVariable = 5;
}

Thanks in advance.

Hi there,

So in the start function, you are redeclaring your ref_TargetScript variable. Another way to phrase this, is that you are declaring a temporary variable. What you really want to do is set your already declared ref_TargetScript variable.

Think of it this way: When you write ‘TargetScript’ in front of your variable on line 12, you’re telling Unity: “Hey, I have a brand new variable that I want to keep track of, but only until the end of this Start function.”

If Unity could reply, it might say: “Great! Oh wait… It looks like you’ve already named a variable the same exact thing, but since it’s not in this method, and since you put the variable type right infront of it you must want a whole different reference!”

However, if you set your already declared variable by simply typing your variable name with an = next to it, you’re telling unity “What I’m about to tell you is what I’d like you to set the above variable to, and I’d like you to hold on to that reference indefinitely.”

In other words, remove ‘TargetScript’ from line 12 - and your scripts will behave as expected.

    public class MyClass : MonoBehaviour
    {
        //This is where we reference our 'other' class.
        public MyOtherClass otherClass;

        void Start()
        {
            //Contrary to what you may think, the declaration below is NOT setting the above reference.
            //This is actually creating a temporary reference which will be destroyed
            //at the end of this start function. 
            //Even if it shares the same exact name, it is in a different SCOPE, 
            //The scope of this temporary variable is only within this method.
            MyOtherClass otherClass = FindObjectOfType<MyOtherClass>(); 

            //Here is how to properly set our above reference:
            otherClass = FindObjectOfType<MyOtherClass>();

            //Notice that we don't redefine our type. We have already defined it above,
            //and a redefinition of the class means that said reference will only exist
            //for this method.
        }
    }
}