修复角色死亡后,依然可以移动的问题,修复角色死亡,敌人将不在追逐,一旦角色死亡后,将关闭角色的碰撞体和寻路
逻辑也比较简单,在角色控制器和AI控制器的更新中加上一个死亡判断就行, if (health.IsDead()) return;
具体代码如下
Health:
-
- using RPG.Core;
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
- using UnityEngine.AI;
-
- // 处理生命值系统的脚本
- namespace RPG.Combat
- {
- public class Health : MonoBehaviour
- {
- [SerializeField] float healthPoints = 100f;// 当前生命值,初始值为 100
-
- bool isDead = false;//是否死亡
-
- //死亡方法,这个方法用于给角色判断,是否继续进行攻击
- public bool IsDead()
- {
- return isDead;
- }
-
- // 处理受伤逻辑的方法
- public void TakeDamage(float damage)
- {
- healthPoints = Mathf.Max(healthPoints - damage, 0);// 减少生命值,确保生命值不会低于 0
- print(healthPoints);
- if (healthPoints == 0)//如果生命值等于0,
- {
- Die();
- }
- }
-
- /// <summary>
- /// 死亡逻辑
- /// </summary>
- private void Die()
- {
- if (isDead) return;//如果玩家已死亡,直接跳出该方法
-
- isDead = true;
- GetComponent<Animator>().SetTrigger("death");//播放死亡动画
- GetComponent<ActionScheduler>().CancelCurrentAction();//设置当前行为为空
- }
- }
- }
-
复制代码
PlayerController:
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
- using RPG.Movement;
- using RPG.Combat;
-
-
-
- //角色的控制
- namespace RPG.Control
- {
-
- public class PlayerController : MonoBehaviour
- {
- private Mover mover;
- Health health;
-
-
- private void Start()
- {
- mover = GetComponent<Mover>();
- health = GetComponent<Health>();
- }
-
- private void Update()
- {
- if (health.IsDead()) return;//如果角色已经死亡,则退出
- if (InteractWithCombat()) return;// 如果处理了战斗交互,则退出方法
- if (InteractWithMovement()) return; // 如果处理了移动交互,则退出方法
-
- }
-
-
-
- private bool InteractWithCombat()// 战斗交互
- {
- RaycastHit[] hits = Physics.RaycastAll(GetMouseRay());
- foreach (RaycastHit hit in hits)
- {
- CombatTarget target = hit.transform.GetComponent<CombatTarget>();//被射线击中的物体获取战斗目标组件
- if(target == null) continue;//如果目标为空,继续执行
-
- if (!GetComponent<Fighter>().CanAttack(target.gameObject))//如果可以攻击该目标,继续执行
- {
- continue;
- }
-
- if(Input.GetMouseButtonDown(0))//按下左键
- {
- GetComponent<Fighter>().Attack(target.gameObject);//攻击目标
-
- }
- return true;//射线找到目标
- }
- return false;//射线没有找到目标 ActionScheduler
- }
-
- // 移动和交互
- private bool InteractWithMovement()
- {
- RaycastHit hit;//存储射线碰撞的信息
- bool hasHit = Physics.Raycast(GetMouseRay(), out hit); //通过射线检测是否有接触到碰撞物体
- if (hasHit)//如果有检测到
- {
- if (Input.GetMouseButton(0))//如果按下鼠标左键
- {
- mover.StartMoveAction(hit.point);
-
- }
- return true;
- }
- return false;
- }
-
-
-
- //创建射线
- private static Ray GetMouseRay()
- {
- return Camera.main.ScreenPointToRay(Input.mousePosition);
-
- }
- }
- }
-
复制代码
AIController
- using RPG.Combat;
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
-
-
- namespace RPG.Control
- {
- //AI的控制
- public class AIController : MonoBehaviour
- {
- [SerializeField] float chaseDistance = 5f;// 设定追逐范围的距离
-
- Fighter fighter;
- Health health;
- GameObject player;
-
- private void Start()
- {
- fighter = GetComponent<Fighter>();
- health = GetComponent<Health>();
- player = GameObject.FindWithTag("Player");// 找到标签为“Player”的游戏对象
- }
-
- private void Update()
- {
- if (health.IsDead()) return;//如果角色已经死亡,则跳出
-
- // 如果和玩家的距离小于设定的追逐范围 并且可以攻击玩家
- if (InAttackRangeOfPlayer()&& fighter.CanAttack(player))
- {
- fighter.Attack(player);//对玩家进行攻击
- print("可以攻击");
- }
- else
- {
- fighter.Cancel();//取消攻击
- }
-
-
- }
-
- private bool InAttackRangeOfPlayer() // 检测是否在攻击范围内
- {
- float distanceToPlayer = Vector3.Distance(player.transform.position,transform.position); // 计算并返回玩家和当前对象之间的距离
- return distanceToPlayer < chaseDistance;//返回两者之间距离是否小于追逐距离
- }
-
-
- }
- }
-
复制代码
Mover
- using RPG.Combat;
- using RPG.Core;
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
- using UnityEngine.AI;
- using UnityEngine.UI;
-
- //角色的移动
- namespace RPG.Movement
- {
-
- public class Mover : MonoBehaviour,IAction
- {
-
- private NavMeshAgent navMeshAgent;
-
- Animator animator;
- Health health;
- CapsuleCollider capsuleCollider;
-
- private void Start()
- {
- animator = GetComponent<Animator>();
- navMeshAgent = GetComponent<NavMeshAgent>();
- health = GetComponent<Health>();
- capsuleCollider = GetComponent<CapsuleCollider>();
- }
-
- private void Update()
- {
- if (health.IsDead())
- {
- capsuleCollider.enabled = false;//关闭碰撞
- navMeshAgent.enabled = false;//关闭寻路
- }
-
- UpdateAnimator();
- }
-
- /// <summary>
- /// 开始移动行为
- /// </summary>
- /// <param name="destination">移动的位置</param>
- public void StartMoveAction(Vector3 destination)
- {
- GetComponent<ActionScheduler>().StartAction(this);
-
- MoveTo(destination);
- }
-
- /// <summary>
- /// 寻路移动到射线检测点
- /// </summary>
- /// <param name="hit"></param>
- public void MoveTo(Vector3 destination)
- {
- navMeshAgent.destination = destination;//获取寻路目的地 = 射线碰撞的点
- navMeshAgent.isStopped = false;
- }
-
- /// <summary>
- /// 停止寻路
- /// </summary>
- public void Cancel()
- {
- navMeshAgent.isStopped = true;
- }
-
-
-
- /// <summary>
- /// 动画更新
- /// </summary>
- private void UpdateAnimator()
- {
- Vector3 velocity = navMeshAgent.velocity;//创建寻路速度
- Vector3 localVelocity = transform.InverseTransformDirection(velocity);// 将世界向前变换到本地空间:
- float speed = localVelocity.z;
-
- animator.SetFloat("forwardSpeed", speed);
- }
- }
- }
复制代码
|