0

Like in here, but the difference is that it's supposed to be done from an instantiated prefab, so I can not drag the GameObject, that has the script with the variable I want to access, into this script.

enter image description here

This was working

public ScriptA script;

void Update() {
   if (script.varX < 0) {
      // . . .
   }
}

But now I'm getting "Object reference not set to an instance of an object" error, which I think comes from the fact that the script trying to access ScriptA, is attached to an instantiated prefab.

How do I attach scripts and/or GameObjects at runtime?

RealAnyOne
  • 125
  • 3
  • 3
  • 17
  • Possible duplicate of [Accessing a variable from another script C#](https://stackoverflow.com/questions/25930919/accessing-a-variable-from-another-script-c-sharp) – Draco18s no longer trusts SE Mar 12 '18 at 19:33
  • It's not a duplicate. I linked that same question in my post, the difference is that I need to access the other script from a prefab GameObject, it can't be done in the same way. – RealAnyOne Mar 13 '18 at 00:08
  • You instantiate a prefab and then with a reference to that clone, given to you by the instantiate method, you....do the thing listed in the dupe target... – Draco18s no longer trusts SE Mar 13 '18 at 00:51

3 Answers3

1

You want to use AddComponent, like:

ScriptA script = gameObject.AddComponent<ScriptA>() as ScriptA;

See the docs here: https://docs.unity3d.com/ScriptReference/GameObject.AddComponent.html

  • 2
    you don't need `as ScriptA` – Basile Perrenoud Mar 12 '18 at 14:27
  • What about attaching a GameObject to the instantiated Prefab? :P – RealAnyOne Mar 12 '18 at 15:46
  • 1
    Assuming the GameObject has already been instantiated, you can use GameObject's `Find`, `FindWithTag`, `FindObjectOfType`, `FindObjectsOfType` to (hopefully) locate it –  Mar 12 '18 at 16:04
  • As to the direct answer to my post: `ScriptA script = gameObject.AddComponent() as ScriptA;` actually adds that script to the gameobject, when I only wanted to access and change some variables. I'll look more into what I have and maybe edit my first post to be clearer, maybe it was my fault in explaining – RealAnyOne Mar 12 '18 at 18:29
1

Looks like you need to find your script type first, if it already exists in the scene:

public ScriptA script;

void Start()
{
    script = GameObject.FindObjectOfType<ScriptA>();
}

void Update()
{
    if(script.variable...)
}
Tom
  • 2,372
  • 4
  • 25
  • 45
  • Why `FindObjectOfType` and not just `.Find` or any of the others? – RealAnyOne Mar 12 '18 at 18:30
  • 1
    @RealAnyOne `Find` returns a GameObject (maybe other objects, I'm unsure) where as `FindObjectOfType` finds the type you are searching for, in this case `ScriptA`. It's safer and quicker than doing`GameObject.Find("YourGameObject").GetComponent()` Another useful one is `FindObjectsOfType` which is plural, so you can populate an array of `ScriptA` types that way, like `ScriptA[] scripts = GameObject.FindObjectsOfType()` – Tom Mar 13 '18 at 08:33
0

Best way to satify the links is fill the fields in the very next lines after you instantiate, that way you can avoid ugly and expenstive Find* calls (I am assuming the script that does the instancing can be made aware of what the target objects are, after all it knows what and where to instantiate)

Its worth noting that newly instantiated scripts' Awake() method will be called before Instantiate() returns, while its Start() will be called at the start of following frame, this is a major difference between the two calls, so if your instantiated script needs the refectences in Awake() you should either refactor (move stuff to Start()) or use Find* as suggested earlier.

zambari
  • 4,797
  • 1
  • 12
  • 22