예제 #1
0
        public void LeaderMoveTo(float x, float y, float z)
        {
            //! To do: This should probably get its own movement generator or use WaypointMovementGenerator.
            //! If the leader's path is known, member's path can be plotted as well using formation offsets.
            if (!m_leader)
            {
                return;
            }

            float pathangle = (float)Math.Atan2(m_leader.GetPositionY() - y, m_leader.GetPositionX() - x);

            foreach (var pair in m_members)
            {
                Creature member = pair.Key;
                if (member == m_leader || !member.IsAlive() || member.GetVictim() || !pair.Value.groupAI.HasAnyFlag((uint)GroupAIFlags.IdleInFormation))
                {
                    continue;
                }

                if (pair.Value.point_1 != 0)
                {
                    if (m_leader.GetCurrentWaypointID() == pair.Value.point_1 - 1 || m_leader.GetCurrentWaypointID() == pair.Value.point_2 - 1)
                    {
                        pair.Value.follow_angle = (float)Math.PI * 2 - pair.Value.follow_angle;
                    }
                }

                float angle = pair.Value.follow_angle;
                float dist  = pair.Value.follow_dist;

                float dx = x + (float)Math.Cos(angle + pathangle) * dist;
                float dy = y + (float)Math.Sin(angle + pathangle) * dist;
                float dz = z;

                GridDefines.NormalizeMapCoord(ref dx);
                GridDefines.NormalizeMapCoord(ref dy);

                if (!member.IsFlying())
                {
                    member.UpdateGroundPositionZ(dx, dy, ref dz);
                }

                if (member.IsWithinDist(m_leader, dist + 5.0f))
                {
                    member.SetUnitMovementFlags(m_leader.GetUnitMovementFlags());
                }
                else
                {
                    member.SetWalk(false);
                }

                member.GetMotionMaster().MovePoint(0, dx, dy, dz);
                member.SetHomePosition(dx, dy, dz, pathangle);
            }
        }
예제 #2
0
        public void MemberAttackStart(Creature member, Unit target)
        {
            GroupAIFlags groupAI = (GroupAIFlags)FormationMgr.CreatureGroupMap[member.GetSpawnId()].groupAI;

            if (groupAI == 0)
            {
                return;
            }

            if (member == m_leader)
            {
                if (!groupAI.HasAnyFlag(GroupAIFlags.MembersAssistLeader))
                {
                    return;
                }
            }
            else if (!groupAI.HasAnyFlag(GroupAIFlags.LeaderAssistsMember))
            {
                return;
            }

            foreach (var pair in m_members)
            {
                if (m_leader) // avoid crash if leader was killed and reset.
                {
                    Log.outDebug(LogFilter.Unit, "GROUP ATTACK: group instance id {0} calls member instid {1}", m_leader.GetInstanceId(), member.GetInstanceId());
                }

                Creature other = pair.Key;

                // Skip self
                if (other == member)
                {
                    continue;
                }

                if (!other.IsAlive())
                {
                    continue;
                }

                if (other.GetVictim())
                {
                    continue;
                }

                if (((other != m_leader && groupAI.HasAnyFlag(GroupAIFlags.MembersAssistLeader)) || (other == m_leader && groupAI.HasAnyFlag(GroupAIFlags.LeaderAssistsMember))) && other.IsValidAttackTarget(target))
                {
                    other.GetAI().AttackStart(target);
                }
            }
        }
예제 #3
0
        public void MemberEngagingTarget(Creature member, Unit target)
        {
            GroupAIFlags groupAI = (GroupAIFlags)FormationMgr.CreatureGroupMap[member.GetSpawnId()].groupAI;

            if (groupAI == 0)
            {
                return;
            }

            if (member == m_leader)
            {
                if (!groupAI.HasAnyFlag(GroupAIFlags.MembersAssistLeader))
                {
                    return;
                }
            }
            else if (!groupAI.HasAnyFlag(GroupAIFlags.LeaderAssistsMember))
            {
                return;
            }

            foreach (var pair in m_members)
            {
                Creature other = pair.Key;

                // Skip self
                if (other == member)
                {
                    continue;
                }

                if (!other.IsAlive())
                {
                    continue;
                }

                if (((other != m_leader && groupAI.HasAnyFlag(GroupAIFlags.MembersAssistLeader)) || (other == m_leader && groupAI.HasAnyFlag(GroupAIFlags.LeaderAssistsMember))) && other.IsValidAttackTarget(target))
                {
                    other.EngageWithTarget(target);
                }
            }
        }