- Home /
Found script for homing missiles, but can't past Null Reference error
This is a script I got off YouTube for making a homing missile. In the video it functions exactly how I want my missiles to function, so I would really like to get it to work. I keep getting a runtime error for "NullReferenceException: Object reference not set to an instance of an object".
I know this means that the script is not finding my enemies in the game and adding them to the 'targets' array, because if it was then the missiles would be working as they should. So the error must be in the line "var targets : GameObject[] = GameObject.FindGameObjectsWithTag("Enemy");" though the error says it is on the "transform.rotation=Quaternion.Slerp...." line.
As far as I can tell it should be finding my enemies which are correctly tagged. Anyone have any ideas as to why the script can't find my enemies?
var speed : float;
var turn : float;
function Update (){
var targets : GameObject[] = GameObject.FindGameObjectsWithTag("Enemy");
var closest : GameObject;
var closestDist = Mathf.Infinity;
for (Target in targets){
var dist = (transform.position - Target.transform.position).sqrMagnitude;
if(dist < closestDist){
closestDist = dist;
closest = Target;
}
}
transform.rotation=Quaternion.Slerp(transform.rotation, Quaternion.LookRotation(closest.transform.postition-transform.position),turn*Time.deltaTime);
transform.position+=transform.forward*speed*Time.deltaTime;
}
I would set a breakpoint in the debugger and see what's co$$anonymous$$g back from the 'find'. If it's truly empty, you must have mistagged them somehow. Perhaps 'enemy' vs 'Enemy' ?
There is nothing co$$anonymous$$g back from the find, but everything is correctly tagged.
I even went into the enemy controller script and put: gameObject.tag = "Enemy"; in the update function so it would assign the correct tag every frame and it still isn't working.
Sorry, meant to reply earlier. Target is each iteration through the targets array. It starts with a capital T because target is a keyword. Probably could be better named, but I just copied it from the example.
Answer by zannghast · Nov 07, 2012 at 12:46 AM
I would check with the line that the debugger had reported the error to occur. That is:
transform.rotation=Quaternion.Slerp(transform.rotation, Quaternion.LookRotation(closest.transform.postition-transform.position),turn*Time.deltaTime);
In this line, the parameter "closest.transform.postition" in the LookRotation method might be the cause. What could be happening is that the object referenced by 'closest' is being destroyed before this actual method call.
To verify this claim, you could maybe print a null check just before that very line with something like:
Debug.Log("Is closest null? " + (closest == null));
Another possible explanation is that 'closest' is not being assigned a reference to any object at all.
*On a totally different note.. why is my original post tagged with my name 'Lee', while this comment is tagged with my account name? Wierd...
The problem is 'targets' is never being populated by the enemies tagged as "Enemy". The 'FindGameObjectsWithTag' function is simply not working and returns null, so closest is always going to be null.
I have double checked the tags on my enemies and tried changing them in Unity and in the script to see if it made a difference. Nothing seems to be working.
Is there maybe a different solution that I can use to find all the Enemy game objects currently in play and put them into an array?
Hmm, in some cases, I create a helper script that contains no function or logic at all. This helps me find the object to which this script is attached to in a fashion similar to what FindGameObjectsWithTag does. So for example, you create an 'Enemy' script (if you haven't already) and attach that to your enemy prefab. Then you could simply find all objects with that component with "var targets : Enemy[] = FindObjectsOfType(Enemy) as Enemy[];" This, however, is very expensive to do in an update loop. Very, very expensive :\
Hmm, are you absolutely sure that 'targets' it not being populated? Have you tried printing out (Debug.Log) it's length after it's assignment in the Update loop?
Yes, I threw "Debug.Log(targets);" right after the FindWithTag and it spams my console with null even when the enemies are on the screen.
Answer by DaveA · Nov 07, 2012 at 01:46 AM
If you want to abandon this, you could set the name of each enemy to Enemy and find all objects by that name, or probably better yet, keep an List of enemy objects as they are created and manage that.
Probably what I'm going to end up having to do, just really disappointed that the "FindObjectsWithTag" function is not working as expected.