Core/Items: Refactor loading additional item data (artifacts/azerite)

Port From (https://github.com/TrinityCore/TrinityCore/commit/ef3485e6fcb669ae3dc3195da5593afcb3091b2a)
This commit is contained in:
hondacrx
2019-11-21 14:54:03 -05:00
parent fafc2c17f9
commit 747899d7db
8 changed files with 242 additions and 139 deletions
+38 -30
View File
@@ -66,60 +66,51 @@ namespace Game.Entities
trans.Append(stmt);
}
public override bool LoadFromDB(ulong guid, ObjectGuid ownerGuid, SQLFields fields, uint entry)
public void LoadAzeriteItemData(AzeriteData azeriteData)
{
if (!base.LoadFromDB(guid, ownerGuid, fields, entry))
return false;
bool needSave = false;
ulong xp = fields.Read<ulong>(43);
uint level = fields.Read<uint>(44);
uint knowledgeLevel = fields.Read<uint>(45);
if (!CliDB.AzeriteLevelInfoStorage.ContainsKey(level))
if (!CliDB.AzeriteLevelInfoStorage.ContainsKey(azeriteData.Level))
{
xp = 0;
level = 1;
knowledgeLevel = GetCurrentKnowledgeLevel();
azeriteData.Xp = 0;
azeriteData.Level = 1;
azeriteData.KnowledgeLevel = GetCurrentKnowledgeLevel();
needSave = true;
}
else if (level > PlayerConst.MaxAzeriteItemLevel)
else if (azeriteData.Level > PlayerConst.MaxAzeriteItemLevel)
{
xp = 0;
level = PlayerConst.MaxAzeriteItemLevel;
azeriteData.Xp = 0;
azeriteData.Level = PlayerConst.MaxAzeriteItemLevel;
needSave = true;
}
if (knowledgeLevel != GetCurrentKnowledgeLevel())
if (azeriteData.KnowledgeLevel != GetCurrentKnowledgeLevel())
{
// rescale XP to maintain same progress %
ulong oldMax = CalcTotalXPToNextLevel(level, knowledgeLevel);
knowledgeLevel = GetCurrentKnowledgeLevel();
ulong newMax = CalcTotalXPToNextLevel(level, knowledgeLevel);
xp = (ulong)(xp / (double)oldMax * newMax);
ulong oldMax = CalcTotalXPToNextLevel(azeriteData.Level, azeriteData.KnowledgeLevel);
azeriteData.KnowledgeLevel = GetCurrentKnowledgeLevel();
ulong newMax = CalcTotalXPToNextLevel(azeriteData.Level, azeriteData.KnowledgeLevel);
azeriteData.Xp = (ulong)(azeriteData.Xp / (double)oldMax * newMax);
needSave = true;
}
else if (knowledgeLevel > PlayerConst.MaxAzeriteItemKnowledgeLevel)
else if (azeriteData.KnowledgeLevel > PlayerConst.MaxAzeriteItemKnowledgeLevel)
{
knowledgeLevel = PlayerConst.MaxAzeriteItemKnowledgeLevel;
azeriteData.KnowledgeLevel = PlayerConst.MaxAzeriteItemKnowledgeLevel;
needSave = true;
}
SetUpdateFieldValue(m_values.ModifyValue(m_azeriteItemData).ModifyValue(m_azeriteItemData.Xp), xp);
SetUpdateFieldValue(m_values.ModifyValue(m_azeriteItemData).ModifyValue(m_azeriteItemData.Level), level);
SetUpdateFieldValue(m_values.ModifyValue(m_azeriteItemData).ModifyValue(m_azeriteItemData.KnowledgeLevel), knowledgeLevel);
SetUpdateFieldValue(m_values.ModifyValue(m_azeriteItemData).ModifyValue(m_azeriteItemData.Xp), azeriteData.Xp);
SetUpdateFieldValue(m_values.ModifyValue(m_azeriteItemData).ModifyValue(m_azeriteItemData.Level), azeriteData.Level);
SetUpdateFieldValue(m_values.ModifyValue(m_azeriteItemData).ModifyValue(m_azeriteItemData.KnowledgeLevel), azeriteData.KnowledgeLevel);
if (needSave)
{
PreparedStatement stmt = DB.Characters.GetPreparedStatement(CharStatements.UPD_ITEM_INSTANCE_AZERITE_ON_LOAD);
stmt.AddValue(0, xp);
stmt.AddValue(1, knowledgeLevel);
stmt.AddValue(2, guid);
stmt.AddValue(0, azeriteData.Xp);
stmt.AddValue(1, azeriteData.KnowledgeLevel);
stmt.AddValue(2, GetGUID().GetCounter());
DB.Characters.Execute(stmt);
}
return true;
}
public override void DeleteFromDB(SQLTransaction trans)
@@ -136,6 +127,16 @@ namespace Game.Entities
return CliDB.AzeriteLevelInfoStorage.LookupByKey(m_azeriteItemData.Level).ItemLevel;
}
uint GetLevel() { return m_azeriteItemData.Level; }
uint GetEffectiveLevel()
{
uint level = m_azeriteItemData.AuraLevel;
if (level == 0)
level = m_azeriteItemData.Level;
return level;
}
uint GetCurrentKnowledgeLevel()
{
// count weeks from 26.06.2019
@@ -277,4 +278,11 @@ namespace Game.Entities
base.ClearUpdateMask(remove);
}
}
public class AzeriteData
{
public ulong Xp;
public uint Level;
public uint KnowledgeLevel;
}
}
+81 -6
View File
@@ -525,7 +525,7 @@ namespace Game.Entities
return true;
}
public void LoadArtifactData(Player owner, ulong xp, uint artifactAppearanceId, uint artifactTier, List<ArtifactPowerLoadInfo> powers)
public void LoadArtifactData(Player owner, ulong xp, uint artifactAppearanceId, uint artifactTier, List<ArtifactPowerData> powers)
{
for (byte i = 0; i <= artifactTier; ++i)
InitArtifactPowers(GetTemplate().GetArtifactID(), i);
@@ -539,7 +539,7 @@ namespace Game.Entities
SetAppearanceModId(artifactAppearance.ItemAppearanceModifierID);
byte totalPurchasedRanks = 0;
foreach (ArtifactPowerLoadInfo power in powers)
foreach (ArtifactPowerData power in powers)
{
power.CurrentRankWithBonus += power.PurchasedRank;
totalPurchasedRanks += power.PurchasedRank;
@@ -585,7 +585,7 @@ namespace Game.Entities
SetArtifactPower((ushort)power.ArtifactPowerId, power.PurchasedRank, power.CurrentRankWithBonus);
}
foreach (ArtifactPowerLoadInfo power in powers)
foreach (ArtifactPowerData power in powers)
{
ArtifactPowerRecord scaledArtifactPowerEntry = CliDB.ArtifactPowerStorage.LookupByKey(power.ArtifactPowerId);
if (!scaledArtifactPowerEntry.Flags.HasAnyFlag(ArtifactPowerFlag.ScalesWithNumPowers))
@@ -2149,7 +2149,7 @@ namespace Game.Entities
return null;
}
void AddArtifactPower(ArtifactPowerLoadInfo artifactPower)
void AddArtifactPower(ArtifactPowerData artifactPower)
{
int index = m_artifactPowerIdToIndex.Count;
m_artifactPowerIdToIndex[artifactPower.ArtifactPowerId] = (ushort)index;
@@ -2183,7 +2183,7 @@ namespace Game.Entities
if (m_artifactPowerIdToIndex.ContainsKey(artifactPower.Id))
continue;
ArtifactPowerLoadInfo powerData = new ArtifactPowerLoadInfo();
ArtifactPowerData powerData = new ArtifactPowerData();
powerData.ArtifactPowerId = artifactPower.Id;
powerData.PurchasedRank = 0;
powerData.CurrentRankWithBonus = (byte)((artifactPower.Flags & ArtifactPowerFlag.First) == ArtifactPowerFlag.First ? 1 : 0);
@@ -2945,13 +2945,88 @@ namespace Game.Entities
}
}
public class ArtifactPowerLoadInfo
public class ArtifactPowerData
{
public uint ArtifactPowerId;
public byte PurchasedRank;
public byte CurrentRankWithBonus;
}
class ArtifactData
{
public ulong Xp;
public uint ArtifactAppearanceId;
public uint ArtifactTierId;
public List<ArtifactPowerData> ArtifactPowers = new List<ArtifactPowerData>();
}
class ItemAdditionalLoadInfo
{
public ArtifactData Artifact;
public AzeriteData AzeriteItem;
public static void Init(Dictionary<ulong, ItemAdditionalLoadInfo> loadInfo, SQLResult artifactResult, SQLResult azeriteItemResult)
{
// 0 1 2 3 4 5
// SELECT a.itemGuid, a.xp, a.artifactAppearanceId, a.artifactTierId, ap.artifactPowerId, ap.purchasedRank FROM item_instance_artifact_powers ap LEFT JOIN item_instance_artifact a ON ap.itemGuid = a.itemGuid ...
if (!artifactResult.IsEmpty())
{
do
{
ItemAdditionalLoadInfo info = new ItemAdditionalLoadInfo();
if (info.Artifact == null)
info.Artifact = new ArtifactData();
info.Artifact.Xp = artifactResult.Read<ulong>(1);
info.Artifact.ArtifactAppearanceId = artifactResult.Read<uint>(2);
info.Artifact.ArtifactTierId = artifactResult.Read<uint>(3);
ArtifactPowerData artifactPowerData = new ArtifactPowerData();
artifactPowerData.ArtifactPowerId = artifactResult.Read<uint>(4);
artifactPowerData.PurchasedRank = artifactResult.Read<byte>(5);
ArtifactPowerRecord artifactPower = CliDB.ArtifactPowerStorage.LookupByKey(artifactPowerData.ArtifactPowerId);
if (artifactPower != null)
{
uint maxRank = artifactPower.MaxPurchasableRank;
// allow ARTIFACT_POWER_FLAG_FINAL to overflow maxrank here - needs to be handled in Item::CheckArtifactUnlock (will refund artifact power)
if (artifactPower.Flags.HasAnyFlag(ArtifactPowerFlag.MaxRankWithTier) && artifactPower.Tier < info.Artifact.ArtifactTierId)
maxRank += info.Artifact.ArtifactTierId - artifactPower.Tier;
if (artifactPowerData.PurchasedRank > maxRank)
artifactPowerData.PurchasedRank = (byte)maxRank;
artifactPowerData.CurrentRankWithBonus = (byte)((artifactPower.Flags & ArtifactPowerFlag.First) == ArtifactPowerFlag.First ? 1 : 0);
info.Artifact.ArtifactPowers.Add(artifactPowerData);
}
loadInfo[artifactResult.Read<ulong>(0)] = info;
} while (artifactResult.NextRow());
}
// 0 1 2 3
// SELECT iz.itemGuid, iz.xp, iz.level, iz.knowledgeLevel FROM item_instance_azerite iz INNER JOIN ...
if (!azeriteItemResult.IsEmpty())
{
do
{
ItemAdditionalLoadInfo info = new ItemAdditionalLoadInfo();
if (info.AzeriteItem == null)
info.AzeriteItem = new AzeriteData();
info.AzeriteItem.Xp = azeriteItemResult.Read<ulong>(1);
info.AzeriteItem.Level = azeriteItemResult.Read<uint>(2);
info.AzeriteItem.KnowledgeLevel = azeriteItemResult.Read<uint>(3);
loadInfo[azeriteItemResult.Read<ulong>(0)] = info;
} while (azeriteItemResult.NextRow());
}
}
}
[StructLayout(LayoutKind.Sequential)]
public class ItemDynamicFieldGems
{