This is Unity screwing with you.
If you do this:
MeshFilter GetMeshFilter()
{
MeshFilter temp = myGo.GetComponent<MeshFilter>();
if ( temp == null ) {
Debug.Log( " > Get Mesh Filter RETURNING NULL" );
return null;
}
return temp;
}
It works.
Why?
Because Unity has overridden Equals
(and the ==
operator) on all Unity objects so that destroyed game objects and never existing objects are both “equal” to null (this was done in an attempt to make developer’s lives easier). But a destroyed (or “missing”) object is not literally null: its a wrapper object in the C# part of the engine pointing at a null object in the underlying C++ code. The null coalescing operator checks for literally null.
For example try this:
Start() {
GameObject gg = new GameObject(); //create a GO
DestroyImmediate(gg); //destroy it immediately
Debug.Log(gg == null); //prints true: it is definitely null!
GameObject go = gg ?? this.gameObject; //get a non-null object
Debug.Log(go); //prints null
}
This is also why you get a MissingReferenceException when you try to access Unity objects that are null, rather than a NullReferenceException: those objects aren’t literally null, but only effectively null.
In general that’s what the Object.bool
operator is used for. Just prefer to use it instead of a null
check:
public static T GetComponentOrAddIfMissing<T>(this GameObject self) where T : Component
{
T component = self.GetComponent<T>();
if(!component) component = self.AddComponent<T>();
return component;
}