Home > database >  Unity GameObject won't MoveTowards prefab
Unity GameObject won't MoveTowards prefab

Time:10-16

I have a GameObject with a RobotMovment script on it that looks like this:

public class RobotMovement : MonoBehaviour {

    private Transform target;
    private float speed = 2f;

    void Start() {
        target = GameObject.FindGameObjectWithTag("Ball").transform;
    }

    void Update() {
        float step = speed * Time.deltaTime;
        transform.position = Vector3.MoveTowards(transform.position, target.position, step);
    }
}

I then have another script placed on a empty game object called Ball that looks like this:

public class Ball : MonoBehaviour {

    public GameObject ballPrefab;

    void Start() {
        var randomPosition = new Vector3(Random.Range(GetComponent<Collider>().bounds.min.x, GetComponent<Collider>().bounds.max.x), 0.25f, Random.Range(GetComponent<Collider>().bounds.min.z, GetComponent<Collider>().bounds.max.z));
        Instantiate(ballPrefab, randomPosition, Quaternion.identity);
    }
}

What I want to achieve is to have the RobotMovement gameobject move towards the ball prefab that gets spawned on the start of the game. Now I get a: nullreferenceexception object reference not set error on start of the game. It might be that the the ball prefabs position can't be read by the RobotMovement script at start?

CodePudding user response:

The Awake() function executes before Start(). It's a good idea to use Awake() to find and assign references such as target, then use Start() for whatever initialisation logic you need once you're confident all your references are in place.

That said, your null reference could be in a number of places, but most likely:

  • No gameobject called "Ball" is found when RobotMovement calls Start().
  • Ball gets destroyed or the reference is lost at some point, and RobotMovement.Update() throws.
  • No collider component on Ball, so Ball.Start() throws.

One thing you didn't ask for, but is important to know, is that GetComponent() is an expensive method to invoke, so you'd be better off calling it just once:

Collider collider = GetComponent<Collider>()
var randomPosition = new Vector3(Random.Range(collider.bounds.min.x, collider.bounds.max.x), 0.25f, Random.Range(collider.bounds.min.z, collider.bounds.max.z));
  • Related