コード例 #1
0
    protected virtual void CheckTarget()
    {
        List <Transform> temp = new List <Transform>();

        for (int i = 0; i < _targetsInVision.Count; i++)
        {
            Transform tar = _targetsInVision[i];
            //排除已消滅的物件
            if (tar != null && !tar.CompareTag(Tags.DeadBody))
            {
                temp.Add(tar);
            }
            else if (tar == npc.attackTarget)
            {
                npc.AttackTargetDie(tar);
            }
        }
        _targetsInVision.Clear();
        _targetsInVision = temp;
        if (guardTarget != null && guardTarget.CompareTag(Tags.DeadBody))
        {
            guardTarget = null;
        }

        temp = new List <Transform>();
        for (int i = 0; i < CommandTargets.Count; i++)
        {
            Transform tar = CommandTargets[i];
            //排除已消滅的物件,死亡物件,非敵對物件
            if (tar != null && !tar.CompareTag(Tags.DeadBody) && !Tags.IsCompanion(this, tar))
            {
                temp.Add(tar);
            }
            else if (npc.attackTarget != null && tar == npc.attackTarget)
            {
                npc.AttackTargetDie(tar);
            }
        }
        CommandTargets.Clear();
        CommandTargets = temp;

        //目標與正前方夾角 小到大
        _targetsInVision.Sort(
            (x, y) =>
            Vector3.Angle(
                Vector3.ProjectOnPlane(myTransform.forward, Vector3.up),
                Vector3.ProjectOnPlane(x.position - myTransform.position, Vector3.up)
                ).CompareTo(
                Vector3.Angle(
                    Vector3.ProjectOnPlane(myTransform.forward, Vector3.up),
                    Vector3.ProjectOnPlane(y.position - myTransform.position, Vector3.up)
                    )));
        List <Transform> orderByAngle = _targetsInVision;

        mainTarget = null;
        //命令對象在視野中
        //MainTarget: 每次回合判斷的攻擊對象
        // 1.嘲諷來源(2),無視太遠的嘲諷
        // 2.範圍內的命令目標
        foreach (Transform commandTarget in CommandTargets)
        {
            if (orderByAngle.Contains(commandTarget))
            {
                mainTarget = commandTarget;
                return;
            }
        }
        if (!IsRanger)
        {
            //進戰找最近
            if (_targetsInVision.Count > 0)
            {
                _targetsInVision.Sort(TargetSorter);
                //進戰找最近的
                foreach (Transform t in _targetsInVision)
                {
                    if (TargetTag.ContainsKey(t.tag))
                    {
                        mainTarget = t;
                        return;
                    }
                }
            }
        }
        else
        {
            //遠程找視野內血最少
            bool overVision = false;
            for (int i = 0; i < orderByAngle.Count; i++)
            {
                Transform t = orderByAngle[i];

                if (TargetTag.ContainsKey(t.tag) && //可攻擊
                    (mainTarget == null || //沒目標
                     t.GetComponent <BaseCharacterBehavior>().status       //血比目前目標少
                     .GetConsumedAttrubute(ConsumedAttributeName.Health).CurValue
                     < mainTarget.GetComponent <BaseCharacterBehavior>().status
                     .GetConsumedAttrubute(ConsumedAttributeName.Health).CurValue))
                {
                    //是否開始超出視野
                    if (!overVision && overVision != Mathf.Abs(Vector3.Angle(    //視野內
                                                                   Vector3.ProjectOnPlane(
                                                                       t.position - myTransform.position, myTransform.up), myTransform.forward))
                        > VisionWidth)
                    {
                        overVision = !overVision;
                        // 3.2.1.遠程範圍(視野)內的血最少目標
                        if (mainTarget != null)
                        {
                            return;
                        }
                    }
                    // 3.2.1.遠程範圍(視野)內的血最少目標
                    // 3.2.2遠程範圍(全)內的血最少目標
                    mainTarget = t;
                }
            }
        }

        if (CommandTargets.Count > 0)
        {
            mainTarget = CommandTargets[0];
        }
        ;
    }