- Home /
How do I access a script component added to a gameobject from an assembly at run-time
In my Unity project, I'm creating a game object and then adding a script to it at run time. The script (called Part in this case) is being added from an assembly. which ends up looking like this in the inspector: Which is not quite the appearance I'm used to seeing on a script component in the inspector. (notice the Unity logo icon.) The script does function as expected though so that part works. The PROBLEM is that when I attempt to access the Part script component on this GameObject from a different script, using the following code:
GameObject newPart = Instantiate(ContentManager.LoadPart(part), loc, Quaternion.Euler(rot)) as GameObject;
newPart.GetComponent<Part>().Load(N["Parts"][i]);
I receive the error shown in the screenshot indicating that "Part" is null.
My second concern is that using this method (adding scripts from assemblies) will prevent me from making a GetComponent call for a base class type and have it successfully access any scripts that inherit from the base class type requested.
So How do I access a script component added at runtime from an assembly? and can it work with inheritance as well?
are you sure you are instantiating a real mesh(not a null)? and what is Content$$anonymous$$anger.LoadPart
Content$$anonymous$$anager.LoadPart is my content management system. it effectively replaces the Resources.Load function. That function returns a GameObject which is just a prefab loaded from an AssetBundle with a "Part.cs" script added from c# assembly(.dll) using System.Reflection before it is returned by LoadPart().
As to my certainty that its being loaded. You can see the part GameObject in the Hierarchy as "core_deck_tile(Clone)" and it does appear in the scene as expected with all expected code behavior. (I just cropped that part out of the image.)
What you're seeing in the inspector the part script is how an added component looks when Unity doesn't know exactly what it is - the same thing happens if you have a private, inner class that inherits from Component, and add it as a component.
I haven't really tried getting those with a GetComponent. Try something like this to figure out what's going on:
GameObject newPart = Instantiate(Content$$anonymous$$anager.LoadPart(part), loc, Quaternion.Euler(rot)) as GameObject;
Component[] comps = newPart.GetComponents<Component>();
foreach(var comp in components) {
Debug.Log("Component: " + comp + " of type: " + comp.GetType());
}
If your Part script doesn't show up, you'll have to be creative. If it does show up, I dunno, it might be that your collection N returns null for the index "Parts"? Is that a dict?
N is a JSONNode from SimpleJSON which I have tested and it is returning the correct value.
I'll have a go at your suggestion to see what it returns and post it here.
Yes. Lord, don't include the same code twice!
The Part component of your newPart object is of the Part type defined in the main dll. The Part type you're checking for with GetComponent is the Part type defined in your local assembly.
So if you do the same loop over the components, but write this ins$$anonymous$$d:
foreach(var comp in components) {
Debug.Log("Component: " + comp + " of type: " + comp.GetType());
Debug.Log("Component is Part: " + (comp is Part));
}
You'll probably get this out:
Component: core_deck_tile(Clone) (Part) of type: Part
Component is Part: False
Now, it's completely fine to have the "core" code in a dll, and include that in your project. In fact, that's a common technique to reduce compilation times. Just don't also include it in the Assets folder, or you will get horrible crashes like this.