예제 #1
0
 private void OnPositionChanged(Object p_sender, EventArgs p_args)
 {
     if (p_sender is Party)
     {
         m_decision   = EMonsterStrategyDecision.CALCULATE_STRATEGY;
         m_targetSlot = null;
     }
     if (p_sender is Monster)
     {
         m_decision = EMonsterStrategyDecision.CALCULATE_STRATEGY;
     }
 }
예제 #2
0
        public virtual void DoTurn(Grid p_grid, Party p_party)
        {
            CalculatesRanged = false;
            if (m_owner.State == Monster.EState.SPAWNING)
            {
                return;
            }
            m_owner.AbilityHandler.ExecuteAttack(null, null, false, EExecutionPhase.BEGIN_OF_MONSTERS_TURN);
            m_owner.AbilityHandler.FlushActionLog(EExecutionPhase.BEGIN_OF_MONSTERS_TURN);
            if (PartyIsCaged(p_grid, p_party))
            {
                m_owner.SkipMovement.Trigger();
                return;
            }
            GridSlot slot      = p_grid.GetSlot(m_owner.Position);
            Boolean  p_isMelee = true;

            m_owner.BuffHandler.ModifyMonsterValues();
            m_owner.CombatHandler.MeleeStrikes          += m_owner.CombatHandler.MeleeStrikesRoundBonus;
            m_owner.CombatHandler.MeleeStrikesRoundBonus = 0;
            if (m_owner.CombatHandler.IsFleeing)
            {
                m_decision = EMonsterStrategyDecision.FLEEING;
            }
            else if (m_decision == EMonsterStrategyDecision.FLEEING)
            {
                m_decision = EMonsterStrategyDecision.CALCULATE_STRATEGY;
            }
            CheckAIEvents();
            if (m_owner.State != Monster.EState.ACTION_FINISHED)
            {
                Boolean flag = DoCastSpell();
                CalculatesRanged = true;
                DoRanged(flag, p_party, p_grid, slot, out p_isMelee);
                CalculatesRanged = false;
                if (flag)
                {
                    p_isMelee            = false;
                    m_owner.RangedAttack = false;
                    m_owner.CombatHandler.Attack();
                    return;
                }
                if (m_decision == EMonsterStrategyDecision.MELEE || m_decision == EMonsterStrategyDecision.CALCULATE_STRATEGY)
                {
                    DoMelee(p_isMelee, p_party, p_grid, slot);
                }
                else if (m_decision == EMonsterStrategyDecision.FLEEING)
                {
                    DoFlee(p_party, p_grid, slot);
                }
            }
            m_owner.SkipMovement.Trigger();
        }
예제 #3
0
 protected virtual void DoMelee(Boolean p_isMelee, Party p_party, Grid p_grid, GridSlot p_startSlot)
 {
     if (p_isMelee)
     {
         m_decision = EMonsterStrategyDecision.MELEE;
         if (m_owner.DistanceToParty <= 1f)
         {
             EDirection direction = EDirectionFunctions.GetDirection(m_owner.Position, p_party.Position);
             if (p_startSlot.GetTransition(direction).TransitionType == EGridTransitionType.CLOSED)
             {
                 if (m_canOpenDoors)
                 {
                     TryOpenDoor(p_startSlot, direction);
                 }
                 return;
             }
             m_owner.RangedAttack = false;
             m_owner.CombatHandler.Attack();
             return;
         }
         else
         {
             if (m_owner.DistanceToParty <= 1.6f)
             {
                 return;
             }
             List <GridSlot> meleeTargets = GetMeleeTargets(p_grid, p_party);
             meleeTargets.Sort(new Comparison <GridSlot>(DistSortAsc));
             if (meleeTargets.Count > 0)
             {
                 if (TryMove(meleeTargets, p_grid, p_startSlot, p_party))
                 {
                     return;
                 }
             }
             else
             {
                 Party    party = LegacyLogic.Instance.WorldManager.Party;
                 GridSlot slot  = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(1, 1));
                 if (slot != null && slot.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot);
                 }
                 GridSlot slot2 = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(-1, -1));
                 if (slot2 != null && slot2.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot2);
                 }
                 GridSlot slot3 = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(-1, 1));
                 if (slot3 != null && slot3.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot3);
                 }
                 GridSlot slot4 = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(1, -1));
                 if (slot4 != null && slot4.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot4);
                 }
                 slot = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(0, 2));
                 if (slot != null && slot.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot);
                 }
                 slot2 = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(2, 0));
                 if (slot2 != null && slot2.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot2);
                 }
                 slot3 = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(-2, 0));
                 if (slot3 != null && slot3.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot3);
                 }
                 slot4 = LegacyLogic.Instance.MapLoader.Grid.GetSlot(party.Position + new Position(0, -2));
                 if (slot4 != null && slot4.IsPassable(m_owner, false))
                 {
                     meleeTargets.Add(slot4);
                 }
                 meleeTargets.RemoveAll((GridSlot t) => t.Position == m_owner.Position);
                 if (meleeTargets.Count > 0 && TryMove(meleeTargets, p_grid, p_startSlot, p_party))
                 {
                     return;
                 }
             }
         }
     }
 }
예제 #4
0
 protected virtual void DoRanged(Boolean p_isMagic, Party p_party, Grid p_grid, GridSlot p_startSlot, out Boolean p_isMelee)
 {
     p_isMelee = true;
     if (m_decision == EMonsterStrategyDecision.RANGED || m_decision == EMonsterStrategyDecision.CALCULATE_STRATEGY)
     {
         if (m_owner.DistanceToParty <= 1.6f)
         {
             m_decision = EMonsterStrategyDecision.MELEE;
             p_isMelee  = true;
         }
         if (!p_isMagic && m_owner.StaticData.SpellRanges > m_owner.CombatHandler.AttackRange && m_owner.DistanceToParty > 1.6f)
         {
             if (m_targetSlot == null)
             {
                 List <GridSlot> rangedTargets = GetRangedTargets(p_grid, p_party, m_owner.StaticData.SpellRanges);
                 if (rangedTargets.Count > 0)
                 {
                     rangedTargets.Sort(new Comparison <GridSlot>(DistSortAsc));
                     if (TryMove(rangedTargets, p_grid, p_startSlot, p_party))
                     {
                         p_isMelee = false;
                         return;
                     }
                     p_isMelee  = true;
                     m_decision = EMonsterStrategyDecision.MELEE;
                 }
                 else
                 {
                     p_isMelee  = true;
                     m_decision = EMonsterStrategyDecision.MELEE;
                 }
             }
         }
         else
         {
             m_decision = EMonsterStrategyDecision.MELEE;
             p_isMelee  = true;
         }
         if (!p_isMagic && m_owner.CombatHandler.AttackRange > 1f && m_owner.DistanceToParty > 1.6f)
         {
             p_isMelee  = false;
             m_decision = EMonsterStrategyDecision.RANGED;
             if (p_grid.LineOfSight(m_owner.Position, p_party.Position, true) && Position.Distance(m_owner.Position, p_party.Position) <= m_owner.CombatHandler.AttackRange && m_owner.DistanceToParty >= 2f)
             {
                 m_owner.CombatHandler.AttackRanged();
                 return;
             }
             if (m_targetSlot == null && (m_owner.Position.X == p_party.Position.X || m_owner.Position.Y == p_party.Position.Y))
             {
                 EDirection direction = EDirectionFunctions.GetDirection(p_party.Position, m_owner.Position);
                 GridSlot   gridSlot  = p_grid.GetSlot(p_party.Position);
                 for (Int32 i = 0; i < m_owner.StaticData.AttackRange; i++)
                 {
                     GridSlot neighborSlot = gridSlot.GetNeighborSlot(p_grid, direction);
                     if (neighborSlot == null)
                     {
                         break;
                     }
                     gridSlot = neighborSlot;
                 }
                 if (gridSlot != null)
                 {
                     m_targetSlot = gridSlot;
                 }
             }
             if (m_targetSlot == null)
             {
                 List <GridSlot> rangedTargets2 = GetRangedTargets(p_grid, p_party);
                 if (rangedTargets2.Count > 0)
                 {
                     rangedTargets2.Sort(new Comparison <GridSlot>(DistSortAsc));
                     if (TryMove(rangedTargets2, p_grid, p_startSlot, p_party))
                     {
                         return;
                     }
                     p_isMelee  = true;
                     m_decision = EMonsterStrategyDecision.MELEE;
                 }
                 else
                 {
                     p_isMelee  = true;
                     m_decision = EMonsterStrategyDecision.MELEE;
                 }
             }
             else
             {
                 if (!(m_owner.Position != m_targetSlot.Position))
                 {
                     p_isMelee  = true;
                     m_decision = EMonsterStrategyDecision.MELEE;
                     return;
                 }
                 if (TryMove(new List <GridSlot>
                 {
                     m_targetSlot
                 }, p_grid, p_startSlot, p_party))
                 {
                     return;
                 }
                 p_isMelee    = true;
                 m_targetSlot = null;
                 m_decision   = EMonsterStrategyDecision.CALCULATE_STRATEGY;
             }
         }
     }
 }