Core/Quests: Improved criteria tree quest objective type
* Fixed _completedObjectives not being cleaned when adding quest * Fixed objective credit being granted if just the criteria tree row containing criteria id was completed (instead of the entire tree linked to objective) * Retroactively grant progress on quest accept for criteria types that require action that cannot be repeated (such as learning a spell) Port From (https://github.com/TrinityCore/TrinityCore/commit/4e89a302fcce7644bcd8cf239edad3b409950438)
This commit is contained in:
@@ -70,18 +70,21 @@ namespace Game.Achievements
|
||||
|
||||
List<Criteria> criteriaList = GetCriteriaByType(type, (uint)miscValue1);
|
||||
foreach (Criteria criteria in criteriaList)
|
||||
UpdateCriteria(criteria, miscValue1, miscValue2, miscValue3, refe, referencePlayer);
|
||||
}
|
||||
|
||||
public void UpdateCriteria(Criteria criteria, ulong miscValue1 = 0, ulong miscValue2 = 0, ulong miscValue3 = 0, WorldObject refe = null, Player referencePlayer = null)
|
||||
{
|
||||
List<CriteriaTree> trees = Global.CriteriaMgr.GetCriteriaTreesByCriteria(criteria.Id);
|
||||
var trees = Global.CriteriaMgr.GetCriteriaTreesByCriteria(criteria.Id);
|
||||
if (!CanUpdateCriteria(criteria, trees, miscValue1, miscValue2, miscValue3, refe, referencePlayer))
|
||||
continue;
|
||||
return;
|
||||
|
||||
// requirements not found in the dbc
|
||||
CriteriaDataSet data = Global.CriteriaMgr.GetCriteriaDataSet(criteria);
|
||||
if (data != null)
|
||||
if (!data.Meets(referencePlayer, refe, (uint)miscValue1, (uint)miscValue2))
|
||||
continue;
|
||||
if (data != null && !data.Meets(referencePlayer, refe, (uint)miscValue1, (uint)miscValue2))
|
||||
return;
|
||||
|
||||
switch (type)
|
||||
switch (criteria.Entry.Type)
|
||||
{
|
||||
// std. case: increment at 1
|
||||
case CriteriaType.WinBattleground:
|
||||
@@ -123,7 +126,7 @@ namespace Game.Achievements
|
||||
case CriteriaType.KillPlayer:
|
||||
case CriteriaType.DeliveredKillingBlow:
|
||||
case CriteriaType.PVPKillInArea:
|
||||
case CriteriaType.WinArena: // This also behaves like CriteriaType.WinAnyRankedArena
|
||||
case CriteriaType.WinArena: // This also behaves like CriteriaType::WinAnyRankedArena
|
||||
case CriteriaType.ParticipateInArena:
|
||||
case CriteriaType.PlayerTriggerGameEvent:
|
||||
case CriteriaType.Login:
|
||||
@@ -202,7 +205,7 @@ namespace Game.Achievements
|
||||
SetCriteriaProgress(criteria, maxSkillvalue, referencePlayer);
|
||||
break;
|
||||
case CriteriaType.CompleteQuestsCount:
|
||||
SetCriteriaProgress(criteria, (uint)referencePlayer.GetRewardedQuestCount(), referencePlayer);
|
||||
SetCriteriaProgress(criteria, (ulong)referencePlayer.GetRewardedQuestCount(), referencePlayer);
|
||||
break;
|
||||
case CriteriaType.CompleteAnyDailyQuestPerDay:
|
||||
{
|
||||
@@ -213,8 +216,8 @@ namespace Game.Achievements
|
||||
{
|
||||
// reset if player missed one day.
|
||||
if (progress != null && progress.Date < (nextDailyResetTime - 2 * Time.Day))
|
||||
SetCriteriaProgress(criteria, 0, referencePlayer);
|
||||
continue;
|
||||
SetCriteriaProgress(criteria, 0, referencePlayer, ProgressType.Set);
|
||||
return;
|
||||
}
|
||||
|
||||
ProgressType progressType;
|
||||
@@ -229,7 +232,7 @@ namespace Game.Achievements
|
||||
progressType = ProgressType.Accumulate;
|
||||
else
|
||||
// last progress is within the day before the reset => Already counted today.
|
||||
continue;
|
||||
return;
|
||||
|
||||
SetCriteriaProgress(criteria, 1, referencePlayer, progressType);
|
||||
break;
|
||||
@@ -245,13 +248,14 @@ namespace Game.Achievements
|
||||
uint counter = 0;
|
||||
|
||||
var rewQuests = referencePlayer.GetRewardedQuests();
|
||||
foreach (var id in rewQuests)
|
||||
foreach (uint rewQuest in rewQuests)
|
||||
{
|
||||
Quest quest = Global.ObjectMgr.GetQuestTemplate(id);
|
||||
Quest quest = Global.ObjectMgr.GetQuestTemplate(rewQuest);
|
||||
if (quest != null && quest.QuestSortID >= 0 && quest.QuestSortID == criteria.Entry.Asset)
|
||||
++counter;
|
||||
}
|
||||
SetCriteriaProgress(criteria, counter, referencePlayer);
|
||||
|
||||
SetCriteriaProgress(criteria, counter, referencePlayer, ProgressType.Highest);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -286,7 +290,7 @@ namespace Game.Achievements
|
||||
{
|
||||
int reputation = referencePlayer.GetReputationMgr().GetReputation(criteria.Entry.Asset);
|
||||
if (reputation > 0)
|
||||
SetCriteriaProgress(criteria, (uint)reputation, referencePlayer);
|
||||
SetCriteriaProgress(criteria, (ulong)reputation, referencePlayer);
|
||||
break;
|
||||
}
|
||||
case CriteriaType.TotalExaltedFactions:
|
||||
@@ -299,9 +303,9 @@ namespace Game.Achievements
|
||||
foreach (var (spellId, _) in referencePlayer.GetSpellMap())
|
||||
{
|
||||
var bounds = Global.SpellMgr.GetSkillLineAbilityMapBounds(spellId);
|
||||
foreach (var skill in bounds)
|
||||
foreach (var skillLineRecord in bounds)
|
||||
{
|
||||
if (skill.SkillLine == criteria.Entry.Asset)
|
||||
if (skillLineRecord.SkillLine == criteria.Entry.Asset)
|
||||
{
|
||||
// do not add couter twice if by any chance skill is listed twice in dbc (eg. skill 777 and spell 22717)
|
||||
++spellCount;
|
||||
@@ -309,6 +313,7 @@ namespace Game.Achievements
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
SetCriteriaProgress(criteria, spellCount, referencePlayer);
|
||||
break;
|
||||
}
|
||||
@@ -329,7 +334,7 @@ namespace Game.Achievements
|
||||
break;
|
||||
case CriteriaType.EarnAchievementPoints:
|
||||
if (miscValue1 == 0)
|
||||
continue;
|
||||
return;
|
||||
SetCriteriaProgress(criteria, miscValue1, referencePlayer, ProgressType.Accumulate);
|
||||
break;
|
||||
case CriteriaType.EarnPersonalArenaRating:
|
||||
@@ -339,13 +344,12 @@ namespace Game.Achievements
|
||||
if (miscValue1 != 0)
|
||||
{
|
||||
if (miscValue2 != reqTeamType)
|
||||
continue;
|
||||
return;
|
||||
|
||||
SetCriteriaProgress(criteria, miscValue1, referencePlayer, ProgressType.Highest);
|
||||
}
|
||||
else // login case
|
||||
{
|
||||
|
||||
for (byte arena_slot = 0; arena_slot < SharedConst.MaxArenaSlot; ++arena_slot)
|
||||
{
|
||||
uint teamId = referencePlayer.GetArenaTeamId(arena_slot);
|
||||
@@ -363,6 +367,7 @@ namespace Game.Achievements
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -440,6 +445,7 @@ namespace Game.Achievements
|
||||
case CriteriaType.ObtainAnyItemWithCurrencyValue:
|
||||
case CriteriaType.EarnExpansionLevel:
|
||||
case CriteriaType.LearnTransmog:
|
||||
default:
|
||||
break; // Not implemented yet :(
|
||||
}
|
||||
|
||||
@@ -451,7 +457,6 @@ namespace Game.Achievements
|
||||
AfterCriteriaTreeUpdate(tree, referencePlayer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void UpdateTimedCriteria(TimeSpan timeDiff)
|
||||
{
|
||||
|
||||
@@ -785,7 +785,7 @@ namespace Game.Entities
|
||||
GetReputationMgr().SetVisible(factionEntry);
|
||||
break;
|
||||
case QuestObjectiveType.CriteriaTree:
|
||||
m_questObjectiveCriteriaMgr.ResetCriteriaTree((uint)obj.ObjectID);
|
||||
m_questObjectiveCriteriaMgr.ResetCriteriaTree(obj);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
|
||||
@@ -9,6 +9,7 @@ using Game.Networking;
|
||||
using Game.Networking.Packets;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace Game
|
||||
{
|
||||
@@ -150,9 +151,11 @@ namespace Game
|
||||
}
|
||||
}
|
||||
|
||||
public void ResetCriteriaTree(uint criteriaTreeId)
|
||||
public void ResetCriteriaTree(QuestObjective questObjective)
|
||||
{
|
||||
CriteriaTree tree = Global.CriteriaMgr.GetCriteriaTree(criteriaTreeId);
|
||||
_completedObjectives.Remove(questObjective.Id);
|
||||
|
||||
CriteriaTree tree = Global.CriteriaMgr.GetCriteriaTree((uint)questObjective.ObjectID);
|
||||
if (tree == null)
|
||||
return;
|
||||
|
||||
@@ -160,6 +163,12 @@ namespace Game
|
||||
{
|
||||
RemoveCriteriaProgress(criteriaTree.Criteria);
|
||||
});
|
||||
|
||||
CriteriaManager.WalkCriteriaTree(tree, criteriaTree =>
|
||||
{
|
||||
if (criteriaTree.Criteria != null && CriteriaManager.GetRetroactivelyUpdateableCriteriaTypes().Contains(criteriaTree.Criteria.Entry.Type))
|
||||
UpdateCriteria(criteriaTree.Criteria, 0, 0, 0, null, _owner);
|
||||
});
|
||||
}
|
||||
|
||||
public override void SendAllData(Player receiver)
|
||||
@@ -274,6 +283,8 @@ namespace Game
|
||||
if (objective == null)
|
||||
return;
|
||||
|
||||
CriteriaTree entireObjectiveTree = Global.CriteriaMgr.GetCriteriaTree((uint)objective.ObjectID);
|
||||
if (IsCompletedCriteriaTree(entireObjectiveTree))
|
||||
CompletedObjective(objective, referencePlayer);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user