Adding a permanent reference to a variable. Is it possible?

Hey everyone.

So I know it’s possible to reference just about every type of class/object by either assigning it in the inspector or grabbing it via GetComponent, but is it possible to have permanent references to the more basic variable types? (i.e. int, float)

Say I have a class that tracks all kinds of data, and I want to add a script that looks for changes in a specific int or float variable of another class, is there a way to assign a reference to an int or float? Assigning it via myFloat = anotherFloat simply assigns it the value during that frame, and I’d rather not run that in Update().

Not possible. Float cannot reference another float.

Classes are Reference-Type. Primitives like int and float are Value-Types.

One common solution is to write a CopyTo function, which copies all of the values from one reference to another.

You could try using events if you don’t want it to be in Update?

public delegate void ValueChangedEvent(float newFloat);

public static event ValueChangedEvent OnFloatChanged;

Then where ever in your code you are changing this float value, put in

if(OnFloatChanged != null)
    OnFloatChanged(changedFloat);

Now, where you’re tracking it, you put in

void OnEnable(){
    <ScriptWhereOriginalFloatIs>.OnFloatChanged += FloatChanged;
}

//and

void OnDisable(){
    <ScriptWhereOriginalFloatIs>.OnFloatChanged -= FloatChanged;
}

Then you’ll need a function CALLED “FloatChanged”.

void FloatChanged(float newFloat){
    trackingFloat = newFloat;
}

The way events work is that, when the original “OnFloatChanged” is called, every script that’s “listening” for it (listeners are added/removed in the OnEnable and OnDisable lines) gets that value originally sent.

It’s like hearing a siren on the road, if you’re listening for it, you drive to the right of the road to get out of the way. If you aren’t listening for it, you don’t do anything.

Unless somebody has a better solution besides using Update, this is all I can think of.

Not sure if it’s what you’re looking for, but you can use properties.

public int number
	{
		get{ return otherObj.otherNum;}
	}

Another way would be to use something like a “proxy” which might use two closures to actually get / set the variable. However that’s a quite unusual case. You would need a good reason to do something like that.

public class VariableProxy<T>
{
    System.Func<T> m_Get;
    System.Action<T> m_Set;
    public VariableProxy(System.Func<T> aGetter, System.Action<T> aSetter)
    {
        m_Get = aGetter;
        m_Set = aSetter;
    }
    public T Value
    {
        get { return m_Get(); }
        set { m_Set(value); }
    }
}

So here you can create an instance of that class and assign two methods to it which actually read and write the value. This allows you to access a single variable in a generic way.

Say you have a script instance “obj” that has a public float variable named “myFloat”. You can do this:

VariableProxy<float> myProxy = new VariableProxy<float>(()=>obj.myFloat, (v)=>obj.myFloat = v);

This class instance “myProxy” can now be used to read and write the myFloat variable

float v = myProxy.Value; // read
myProxy.Value = 5f; // write

Since myProxy is a class you can pass it’s reference around and store it whereever you want. So if you have different classes with different float variables you can create a proxy for each and put those proxies in an array / List. Now you can access them in a generic way. How you organise or differentiate them is of course up to you ^^.