【问题标题】:Collider.Enabled error: true and then false loopCollider.Enabled 错误:真然后假循环
【发布时间】:2021-07-20 00:51:47
【问题描述】:

我试图让我的动画敌人(子对象)在 enemieDeath == true 时禁用它的对撞机。我写了一个 debug.log,上面写着“碰撞器。启用 = 真,碰撞器。启用 = 假,在我的玩家与敌人孩子(有动画)碰撞后,它会在无限循环中执行此操作。

这是我正在使用的脚本。

EnemieMove 脚本

//参考PlayerController脚本

            if (playerControllerScript.enemieDeath == true)
        {
            goblinCollider.enabled = !goblinCollider.enabled;
            enemieAnimator.SetBool("IsDead", true);
            Debug.Log("Collider.enabled = " + goblinCollider.enabled);
        }
    }

播放器控制器脚本

        void FixedUpdate()
        {

         int layerMask = 1 << 8;
         int layerMaskCollectable = 1 << 9;
         RaycastHit hit;

         if (Physics.Raycast(transform.position, transform.TransformDirection(Vector3.down), out hit, 1.5f, layerMask))
        {
           Debug.DrawRay(transform.position, transform.TransformDirection(Vector3.down) * hit.distance, Color.yellow);
           Debug.Log("Did Hit");
           enemieDeath = true;
           //Destroy(hit.transform.gameObject); 
           playerRb.AddForce(Vector3.up * bounceForce, ForceMode.Impulse);
           gameManager.UpdateScore(20);
            
        }

【问题讨论】:

    标签: c# unity3d


    【解决方案1】:

    您没有发布第一个代码块的确切执行位置,但从行为我可以猜测它在 UpdateFixedUpdate (或其他任何重复调用的内容)内。

    因此,一旦您将 playerControllerScript.enemieDeath 设置为 true,它将在每次切换启用值时一遍又一遍地执行。

    一个快速的解决方法是检查和设置

    if (playerControllerScript.enemieDeath && goblinCollider.enabled)
    {
        goblinCollider.enabled = false;
        enemieAnimator.SetBool("IsDead", true);
        Debug.Log("Collider.enabled = " + goblinCollider.enabled);
    }
    

    作为更一般的修复:停止轮询检查布尔标志!而是让您的代码事件驱动并在事件实际发生时禁用碰撞器等ONCE

    有例如

    public class PlayerController : MonoBehaviour
    {
        public event Action OnEnemyDied;
    
        private void FixedUpdate ()
        {
            ...
    
            if (Physics.Raycast(transform.position, transform.TransformDirection(Vector3.down), out hit, 1.5f, layerMask))
            {
               ...
    
               OnEnemyDied?.Invoke();
            }
        }
    
        ...
    }
    

    通过这种方式,您可以简单地注册一个回调,该回调仅在调用此事件时才会执行,例如

    public class EnemyMove : MonoBehaviour
    {
        [SerializeField] private PlayerController playerControllerScript;
    
        private void Awake ()
        {
            playerControllerScript.OnEnemyDied += OnEnemyDied;
        }
    
        private void OnEnemyDied ()
        {
            if(golblinCollider.enabled)
            {
                goblinCollider.enabled = false;
                enemieAnimator.SetBool("IsDead", true);
                Debug.Log("Collider.enabled = " + goblinCollider.enabled);
            }
        }
    
        ...
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-06-12
      • 2014-02-17
      • 1970-01-01
      • 1970-01-01
      • 2011-01-23
      • 1970-01-01
      • 1970-01-01
      • 2013-08-22
      相关资源
      最近更新 更多