Search code examples
c#unity-game-enginetriggers

Unity - Getting different results when calling the same method from separate scripts


I am trying to make a snake-like game where you control a snake "head" and eat little cubes of food that randomly spawn on the map one at a time. Each food item should disappear after it comes in contact with the player and then a new food item should spawn. I created a prefab for the food, and a spawner game object that instantiates the prefab according to the collision situation.

I got to the part where the prefab detects something is happening, and so I added some Debug.Log() lines to test whether the boolean "eaten" is true or false (false by default and only true when the OnTriggerEnter2D() method is activated).

I've been attempting to debug my code and have noticed that this method "public bool GetTriggerCondition()" actually gives me different results when it is called from its own script, versus when I call it from the spawner object's script. The triggering seems to play well with other methods being called from the same script, but when I call it from another script I only get a false return even if there is a trigger event.

Here are the scripts at play here:

public class FoodTrigger_Script : MonoBehaviour
{
    public bool eaten = false;

    public void OnTriggerEnter2D(Collider2D collision)
    {
        SetTriggerTrue();
        Debug.Log(GetTriggerCondition());
    }

    public bool GetTriggerCondition()
    {
        bool result = eaten;
        return result;
    }

    public void SetTriggerFalse()
    {
        eaten = false;
    }
    private void SetTriggerTrue()
    {
        eaten = true;
        Debug.Log("TRUEEEE");
    }
}
public class FoodSpawner_Script : MonoBehaviour
{ 
    [SerializeField] GameObject snakeHead;
    private GameObject tempFood;
    FoodTrigger_Script foodTrigger;
    [SerializeField] GameObject foodPrefab;

    // Start is called before the first frame update
    void Awake()
    {
        foodTrigger = foodPrefab.GetComponent<FoodTrigger_Script>();
    }

    void Start()
    {
        SpawnFood();
    }

    // Update is called once per frame
    void Update()
    {
        ProcessFood();
    }

    void SpawnFood()
    {
        tempFood = Instantiate(foodPrefab, new Vector3(Random.Range(-8,8), Random.Range(-4, 4),0), transform.rotation);
    }

    void ProcessFood ()
    {
        Debug.Log(foodTrigger.GetTriggerCondition());
    }
}

Console results

As you can see from the console image, the test logs are coming back as false constantly, and then the true logs are processed correctly, and then the false logs from the "FoodSpawner_Script" continue. Not sure what I'm doing wrong, so any suggestions are helpful! Thanks.


Solution

  • The different results you're seeing are because you're getting the information from two different instances of the FoodTrigger_Script.

    The FoodSpawner_Script is talking to the FoodTrigger_Script attached to the foodPrefab and not the instantiated version in the scene.

    So in ProcessFood you should be calling tempFood.GetComponent<FoodTrigger_Script>().GetTriggerCondition(), instead of foodTrigger.GetTriggerCondition()

    Or better yet, store a reference to the script instance on tempFood when you instantiate it in SpawnFood. (It looks like you already tried to do something like this. Very close)

    public class FoodSpawner_Script : MonoBehaviour
    { 
        [SerializeField] GameObject snakeHead;
        FoodTrigger_Script foodTrigger;
        [SerializeField] GameObject foodPrefab;
    
        void Start()
        {
            SpawnFood();
        }
    
        // Update is called once per frame
        void Update()
        {
            ProcessFood();
        }
    
        void SpawnFood()
        {
            GameObject tempFoodObject = Instantiate(foodPrefab, new Vector3(Random.Range(-8,8), Random.Range(-4, 4),0), transform.rotation);
            foodTrigger = tempFoodObject.GetComponent<FoodTrigger_Script>();
        }
    
        void ProcessFood ()
        {
            Debug.Log(foodTrigger.GetTriggerCondition());
        }
    }