unity3D-攻击移动
1. 首先是人物的挂载文件
// 定义变量
private IBattleCharacterContainer AttackTargetInfo = null; // 攻击目标信息集合 public Transform AttackTargetTrans = null; // 攻击目标transform private Vector2 MoveDistance = new Vector2 (4, 6); //攻击后向后的移动距离 private Vector2 MoveDirLeft = new Vector2 (-70, -30); // 攻击后相对目标的移动角度 private Vector2 MoveDirRigh = new Vector2 (30, 70); // 攻击后相对目标的移动角度 bool moveFlag = false; // 是否移动控制变量
float m_refcomSmoothTime = 0.8f; // 移动所需要的时间 Vector3 m_refFix = Vector3.zero; Vector3 moveToPos = Vector3.zero; // 计算后的移动位置
// 对外接口1 攻击目标的设定
public void SetTargetInfo(IBattleCharacterContainer target) { this.AttackTargetInfo = target; this.AttackTargetTrans = target.Controller.transform; }
// 攻击后移动的位置设置
void setMosterMoveTo () { float angle = UnityEngine.Random.Range(1, 3)== 1 ? UnityEngine.Random.Range (MoveDirLeft.x, MoveDirLeft.y) : UnityEngine.Random.Range (MoveDirRigh.x, MoveDirRigh.y); float distance = Math.Abs(angle) * MoveDistance.y / MoveDirRigh.y; transform.LookAt (AttackTargetTrans); Quaternion r0= Quaternion.Euler(transform.rotation.eulerAngles.x, transform.rotation.eulerAngles.y + angle, transform.rotation.eulerAngles.z); Vector3 movePos = (transform.position + (r0 * Vector3.forward) * distance); moveFlag = true; moveToPos = movePos; }
// 攻击后移动的位置移动
void setMovetoPos () { transform.position = Vector3.SmoothDamp(transform.position, moveToPos, ref m_refFix, m_refcomSmoothTime); transform.LookAt (AttackTargetTrans); m_refcomSmoothTime -= Time.deltaTime; if(m_refcomSmoothTime <= 0) { m_refcomSmoothTime = 0.8f; transform.position = moveToPos; moveFlag = false; } }
3. Update 中人物正常移动的AI
private bool isMoving; public void Update() { float step = motionSpeed * Time.deltaTime; var motionDir = LookTarget - transform.position; if(motionDir.magnitude > Mathf.Epsilon) { var lookTowards = Quaternion.LookRotation(motionDir); transform.rotation = Quaternion.Slerp(transform.rotation, lookTowards, step); } if (CanMove) { if(AttackTargetTrans != null) { if(AttackTargetInfo.CharacterVariableData.Hp <= 0) { moveFlag = false; AttackTargetTrans = null; return; } else if(moveFlag == false && Vector3.Distance(transform.position, AttackTargetTrans.position) <= 5) { setMosterMoveTo(); return; } else if(moveFlag == true) { setMovetoPos(); return; } } var newPos = Vector3.MoveTowards(transform.position, Target, step); transform.position = new Vector3(newPos.x, transform.position.y, newPos.z); var d = Vector3.Distance(newPos, Target); if (d <= 1.0f && isMoving) { isMoving = false; OnReachedMoveTarget(EventArgs.Empty); } } }
Event ·登录
public event EventHandler ReachedMoveTarget; protected virtual void OnReachedMoveTarget(EventArgs e) { var handler = ReachedMoveTarget; if (handler != null) handler(this, e); }
控制移动
Controller.ReachedMoveTarget += characterController_ReachedMoveTarget;
private bool isNavigationStopped; private void characterController_ReachedMoveTarget(object sender, EventArgs e) { if (rail == null || isNavigationStopped) { Controller.Idle(); return; } MoveOn(); } private const float minRandomRadius = 2.0f; private const float maxRandomRadius = 5.0f; private void MoveOn() { if (rail == null) return; if (currentRailNodeIndex >= rail.Length - 1) return; currentRailNodeIndex++; var pos = rail[currentRailNodeIndex]; var randomAngle = UnityEngine.Random.Range(0.0f, Mathf.PI * 2.0f); var randomRadius = UnityEngine.Random.Range(minRandomRadius, maxRandomRadius); var offsetX = Mathf.Cos(randomAngle) * randomRadius; var offsetZ = Mathf.Sin(randomAngle) * randomRadius; Controller.SetTarget(new Vector3(pos.x + offsetX, groundPosition, pos.z + offsetZ)); }
public void SetTarget(Vector3 target) { Target = target; LookTarget = target; isMoving = true; }