Core/Groups: Fixes groups staying linked with players.

This commit is contained in:
Hondacrx
2025-09-02 22:43:56 -04:00
parent 6531cd9dc1
commit 3d23a9f162
34 changed files with 385 additions and 402 deletions
+21 -27
View File
@@ -104,27 +104,24 @@ namespace Game.Entities
if (group != null)
{
// 2. In case when player is in group, initialize variables necessary for group calculations:
for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
foreach (GroupReference groupRef in group.GetMembers())
{
Player member = refe.GetSource();
if (member != null)
Player member = groupRef.GetSource();
if (killer == member || (member.IsAtGroupRewardDistance(_victim) && member.IsAlive()))
{
if (killer == member || (member.IsAtGroupRewardDistance(_victim) && member.IsAlive()))
{
uint lvl = member.GetLevel();
// 2.1. _count - number of alive group members within reward distance;
++_count;
// 2.2. _sumLevel - sum of levels of alive group members within reward distance;
_sumLevel += lvl;
// 2.3. _maxLevel - maximum level of alive group member within reward distance;
if (_maxLevel < lvl)
_maxLevel = (byte)lvl;
// 2.4. _maxNotGrayMember - maximum level of alive group member within reward distance,
// for whom victim is not gray;
uint grayLevel = Formulas.GetGrayLevel(lvl);
if (_victim.GetLevelForTarget(member) > grayLevel && (_maxNotGrayMember == null || _maxNotGrayMember.GetLevel() < lvl))
_maxNotGrayMember = member;
}
uint lvl = member.GetLevel();
// 2.1. _count - number of alive group members within reward distance;
++_count;
// 2.2. _sumLevel - sum of levels of alive group members within reward distance;
_sumLevel += lvl;
// 2.3. _maxLevel - maximum level of alive group member within reward distance;
if (_maxLevel < lvl)
_maxLevel = (byte)lvl;
// 2.4. _maxNotGrayMember - maximum level of alive group member within reward distance,
// for whom victim is not gray;
uint grayLevel = Formulas.GetGrayLevel(lvl);
if (_victim.GetLevelForTarget(member) > grayLevel && (_maxNotGrayMember == null || _maxNotGrayMember.GetLevel() < lvl))
_maxNotGrayMember = member;
}
}
// 2.5. _isFullXP - flag identifying that for all group members victim is not gray,
@@ -254,15 +251,12 @@ namespace Game.Entities
_groupRate = Formulas.XPInGroupRate(_count, isRaid);
}
// 3.1.3. Reward each group member (even dead or corpse) within reward distance.
for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
foreach (GroupReference groupRef in group.GetMembers())
{
Player member = refe.GetSource();
if (member != null)
{
// Killer may not be at reward distance, check directly
if (killer == member || member.IsAtGroupRewardDistance(_victim))
_RewardPlayer(member, isDungeon);
}
Player member = groupRef.GetSource();
// Killer may not be at reward distance, check directly
if (killer == member || member.IsAtGroupRewardDistance(_victim))
_RewardPlayer(member, isDungeon);
}
}
}
+2 -5
View File
@@ -40,12 +40,9 @@ namespace Game.Entities
Group group = GetGroup();
if (group != null)
{
for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
foreach (GroupReference groupRef in group.GetMembers())
{
Player player = refe.GetSource();
if (player == null)
continue;
Player player = groupRef.GetSource();
if (!player.IsAtGroupRewardDistance(pRewardSource))
continue; // member (alive or dead) or his corpse at req. distance
+14 -14
View File
@@ -18,14 +18,14 @@ namespace Game.Entities
List<Player> nearMembers = new();
for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
foreach (GroupReference groupRef in group.GetMembers())
{
Player Target = refe.GetSource();
Player target = groupRef.GetSource();
// IsHostileTo check duel and controlled by enemy
if (Target != null && Target != this && IsWithinDistInMap(Target, radius) &&
!Target.HasInvisibilityAura() && !IsHostileTo(Target))
nearMembers.Add(Target);
if (target != this && IsWithinDistInMap(target, radius) &&
!target.HasInvisibilityAura() && !IsHostileTo(target))
nearMembers.Add(target);
}
if (nearMembers.Empty())
@@ -37,13 +37,13 @@ namespace Game.Entities
public PartyResult CanUninviteFromGroup(ObjectGuid guidMember, byte? partyIndex)
{
Group grp = GetGroup(partyIndex);
if (grp == null)
Group group = GetGroup(partyIndex);
if (group == null)
return PartyResult.NotInGroup;
if (grp.IsLFGGroup())
if (group.IsLFGGroup())
{
ObjectGuid gguid = grp.GetGUID();
ObjectGuid gguid = group.GetGUID();
if (Global.LFGMgr.GetKicksLeft(gguid) == 0)
return PartyResult.PartyLfgBootLimit;
@@ -51,7 +51,7 @@ namespace Game.Entities
if (Global.LFGMgr.IsVoteKickActive(gguid))
return PartyResult.PartyLfgBootInProgress;
if (grp.GetMembersCount() <= SharedConst.LFGKickVotesNeeded)
if (group.GetMembersCount() <= SharedConst.LFGKickVotesNeeded)
return PartyResult.PartyLfgBootTooFewPlayers;
if (state == LfgState.FinishedDungeon)
@@ -62,8 +62,8 @@ namespace Game.Entities
return PartyResult.PartyLfgBootLootRolls;
// @todo Should also be sent when anyone has recently left combat, with an aprox ~5 seconds timer.
for (GroupReference refe = grp.GetFirstMember(); refe != null; refe = refe.Next())
if (refe.GetSource() != null && refe.GetSource().IsInMap(this) && refe.GetSource().IsInCombat())
foreach (GroupReference groupRef in group.GetMembers())
if (groupRef.GetSource().IsInMap(this) && groupRef.GetSource().IsInCombat())
return PartyResult.PartyLfgBootInCombat;
/* Missing support for these types
@@ -73,13 +73,13 @@ namespace Game.Entities
}
else
{
if (!grp.IsLeader(GetGUID()) && !grp.IsAssistant(GetGUID()))
if (!group.IsLeader(GetGUID()) && !group.IsAssistant(GetGUID()))
return PartyResult.NotLeader;
if (InBattleground())
return PartyResult.InviteRestricted;
if (grp.IsLeader(guidMember))
if (group.IsLeader(guidMember))
return PartyResult.NotLeader;
}
+4 -5
View File
@@ -2442,12 +2442,11 @@ namespace Game.Entities
var group = GetGroup();
if (group != null)
{
for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
foreach (GroupReference groupRef in group.GetMembers())
{
Player player = refe.GetSource();
Player player = groupRef.GetSource();
// for any leave or dead (with not released body) group member at appropriate distance
if (player != null && player.IsAtGroupRewardDistance(pEventObject) && player.GetCorpse() == null)
if (player.IsAtGroupRewardDistance(pEventObject) && player.GetCorpse() == null)
player.AreaExploredOrEventHappens(questId);
}
}
@@ -3481,7 +3480,7 @@ namespace Game.Entities
{
if (IsQuestRewarded(questObjective.QuestID) || IsQuestObjectiveComplete(questObjective.QuestID, questObjective.Id))
return SpawnTrackingState.Complete;
if (GetQuestStatus(questObjective.QuestID) != QuestStatus.None && IsQuestObjectiveCompletable(questObjective.QuestID, questObjective.Id))
{
var itr = m_QuestStatus.LookupByKey(questObjective.QuestID);
+5 -5
View File
@@ -147,6 +147,9 @@ namespace Game.Entities
WorldMgr.DecreasePlayerCount();
m_group.Dispose();
m_originalGroup.Dispose();
base.Dispose();
}
@@ -7531,12 +7534,9 @@ namespace Game.Entities
Group group = GetGroup();
if (group != null)
{
for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
foreach (GroupReference groupRef in group.GetMembers())
{
Player player = refe.GetSource();
if (player == null)
continue;
Player player = groupRef.GetSource();
if (!player.IsAtRecruitAFriendDistance(this))
continue; // member (alive or dead) or his corpse at req. distance