如何在不影响共享该脚本的所有其他游戏对象的情况下更改共享脚本中的变量?

How to change a variable in a shared script, without affecting all the other game objects that share that script?

我整天都在努力解决这个问题,因为我不想为每颗子弹制作一个单独的脚本,而是我想要一个单一的 EnemyBulletMovement 脚本,它可以以不同的方式移动每颗子弹,具体取决于在我实例化它时输入的 BulletType int 上。

问题是,如果我同时发射多颗子弹,它们将在另一颗子弹实例化后立即更改 BulletType,因为它们都共享同一个脚本。

我的目标是让所有项目符号都有一个私有脚本,但无论我尝试什么,每次我尝试只为其中一个项目符号更改变量时,所有活动项目符号的变量仍然会更改。

实例化子弹并赋予它们 BulletType 值的 EnemyController 脚本:

 GameObject enemyBullet = ObjectPooler.SharedInstance.GetPooledEnemyBullet();
        if (enemyBullet != null)
        {
            Quaternion rotationAmount = Quaternion.Euler(0, 0, 0);
            Quaternion postRotation = transform.rotation * rotationAmount;
            enemyBullet.transform.position = transform.position;
            enemyBullet.transform.rotation = postRotation;
            enemyBullet.SetActive(true);
            enemyBullet.GetComponent<EnemyBulletMovement>().SetBullet(2);

        }
        GameObject enemyBullet2 = ObjectPooler.SharedInstance.GetPooledEnemyBullet();
        if (enemyBullet2 != null)
        {
            Quaternion rotationAmount = Quaternion.Euler(0, 3, 0);
            Quaternion postRotation = transform.rotation * rotationAmount;
            enemyBullet2.transform.position = transform.position;
            enemyBullet2.transform.rotation = postRotation;
            enemyBullet2.SetActive(true);
            enemyBullet2.GetComponent<EnemyBulletMovement>().SetBullet(0);
        }

共享 EnemyBulletMotion 脚本,从上述脚本中获取 bulletType。这是问题所在:

public void SetBullet(int typeIndex)
{
    bulletType = typeIndex;
    Debug.Log(bulletType);
}
private void BulletMotion()
{
    
    if (bulletType == 0)
    {
        rb.velocity = pos;
    }
    if (bulletType == 1)
    {
        axis = Mathf.Sin(Time.deltaTime * -frequency) * magnitude * transform.up;  // Up down Wave motion
        transform.Rotate(Vector3.forward * sideMag);                               // Side Sway Motion (+ Wave = Spiral Motion)
        rb.velocity = pos + axis;                                                  // Combine all Motions
    }
    if (bulletType == 2)
    {
        Debug.Log("Shootin");
        axis = Mathf.Sin(Time.deltaTime * -frequency) * magnitude * transform.up;  // Up down Wave motion
        transform.Rotate(Vector3.forward * -sideMag);                              // Side Sway Motion (+ Wave = Spiral Motion)
        rb.velocity = pos + axis;                                                  // Combine all Motions
    }

}

编辑:虽然这个调试 Shootin 从未出现在我的控制台中,所以也许 bulletType 在这里没有被正确读取?为了澄清,第一个 Debug.Log(bulletType); return 一个 0 或一个 2 所以它正在工作。但是第二个 Debug.Log("Shootin"); 永远不会打印出来。

我尝试了私有的、静态的,并从整个 EnemyBulletMovement 脚本中创建了一个实例,但没有任何效果。

当我调试这段代码时,脚本可以运行,bulletType 将从 2 变为 0 并返回,但是当它发生时它会改变两颗子弹,所以它们会以相同的方式飞行,而我想要的是让每颗子弹跟随自己的运动。如果没有办法做到这一点,我将不得不为每个 bulletmotion 创建一个单独的脚本,但我在这里只显示 2 个,我已经有很多,这就是为什么我想尝试一下并使其与 if statements 稍后再使用 case statements

编辑:在下方添加了 ObjectPooler 脚本。

public List<GameObject> pooledEnemyBullets;
public GameObject EnemyBulletToPool;
public int EnemyBulletAmountToPool;
  pooledEnemyBullets = new List<GameObject>();
public static ObjectPooler SharedInstance;

void Awake()
{
    SharedInstance = this;
}


void Start()
{
    for (int i = 0; i < EnemyBulletAmountToPool; i++)
    {
        GameObject obj3 = (GameObject)Instantiate(EnemyBulletToPool);
        obj3.SetActive(false);
        pooledEnemyBullets.Add(obj3);
    }
}
public GameObject GetPooledEnemyBullet()
{
    //1
    for (int i = 0; i < pooledEnemyBullets.Count; i++)
    {
        //2
        if (!pooledEnemyBullets[i].activeInHierarchy)
        {
            return pooledEnemyBullets[i];
        }
    }
    //3   
    return null;
}
}

子弹类型应声明为private int bulletType。如果您将项目符号类型声明为 private static int bulletType,则所有项目符号都相同。

如果它已经被声明为private int bulletType,那么你应该检查你使用对象池的逻辑。您可能正在一遍又一遍地处理同一个子弹,或者处理池中的所有子弹。