Collider works from time to time...

Hi, I’m new in Unity Scripting and English is not my native language. I have two scripts: “Attack_Sphere” and “Battle_System”

Attack_Sphere is a script that parent to Sphere with trigger collider. I use it to find “enemies” that collide with this sphere.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Attack_Sphere : MonoBehaviour
{

    public List<Collider> colliders = new List<Collider>();   
  
    // Start is called before the first frame update
    void Start()
    {
       
    }

    // Update is called once per frame
    void Update()
    {
        transform.Rotate(0f, 0.1f, 0f); //Just for fun
    }

    public void OnTriggerEnter(Collider other)
    {
       
        if (!colliders.Contains(other)&other.CompareTag("Enemy"))
        {
            colliders.Add(other);
           
        }
        colliders.ForEach(print);       
    }

}

Battle_System is a script that parent to my “Player” Prefab. It’s goal to get list of enemies from Attack_Sphere. It works, but not correctly. For some reason even if there are some collide, Battle_System doesn’t want to correctly register it, says that list has not any elements. But if u look in List you can see that there are elements in it. Why does it happen?

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Battle_System : MonoBehaviour
{
    public GameObject AimSprite;   
   
    private bool AimActive;
    private GameObject targetCurrent;
    private GameObject aSphere;
    private Attack_Sphere aSphereScript;
    public List<Collider> enemies;
    public int enemiesNumber;
    private Collider activeEnemy;
    private Transform enemyPos;
    private int eIndex = 0;


    // Start is called before the first frame update
    void Start()
    {
        StartCoroutine(AimActiveWait());
    }

    // Update is called once per frame
    void Update()
    {
        AimActive = Player_movement.aimActive;       
    }

    IEnumerator AimActiveWait()
    {
        yield return new WaitWhile(() => AimActive != true);
        StartCoroutine(AimDisactivateWait());
        MainBody();
    }

    IEnumerator AimDisactivateWait()
    {
        yield return new WaitWhile(() => AimActive != false);
        BattleCancel();
        StartCoroutine(AimActiveWait());
    }

    void MainBody()
    {
        aSphere = GameObject.FindGameObjectWithTag("AttackRad");
        aSphereScript = aSphere.GetComponentInChildren<Attack_Sphere>();
        enemies = aSphereScript.colliders;
        enemiesNumber = enemies.Count;
       
        print(enemies);
        print("There are # of Enemies = " + enemiesNumber);
        enemies.ForEach(print);

        if (enemiesNumber != 0)
        {
            print("There are some enemies, about " + enemiesNumber);
            activeEnemy = enemies[eIndex];            
            enemyPos = activeEnemy.transform;
            targetCurrent = Instantiate(AimSprite, enemyPos);
        }
    }

    void BattleCancel()
    {
        Destroy(targetCurrent);
    }
}

There is example how it looks like in Editor Inspector:
8126636--1053902--upload_2022-5-14_3-26-39.png

Hah! This is a fun one. So:

In ‘MainBody’, which is called once each time AimActive becomes true, you:

  • Grab the list of enemies from Attack_Sphere
  • Count how many enemies are in the list right then, and store it in enemiesNumber.

So far, so good.

HOWEVER

‘enemies’ now contains a reference to the same list that is stored in Attack_Sphere. It’s not a copy of the list, it’s a reference to it. So if enemies get added to the list when they collide with Attack_Sphere, they’ll show up in the ‘enemies’ list in your Battle_System. But because you aren’t calling MainBody(), enemiesNumber is not updated.