Core/Players: Implemented PlayerDataElementAccount, PlayerDataElementCharacter, PlayerDataFlagAccount and PlayerDataFlagCharacter

Port From (https://github.com/TrinityCore/TrinityCore/commit/60400d25f5fff2dabd4aa74bbdbc0d2370360a35)
This commit is contained in:
Hondacrx
2025-08-19 16:29:13 -04:00
parent df197587a3
commit a9fc9f454f
18 changed files with 710 additions and 26 deletions
+147 -1
View File
@@ -575,6 +575,7 @@ namespace Game.Entities
// TODO: finish dragonriding - this forces old flight mode
AddAura(404468, this);
}
bool _LoadHomeBind(SQLResult result)
{
PlayerInfo info = Global.ObjectMgr.GetPlayerInfo(GetRace(), GetClass());
@@ -650,6 +651,80 @@ namespace Game.Entities
return true;
}
void _LoadPlayerData(SQLResult elementsResult, SQLResult flagsResult)
{
if (!elementsResult.IsEmpty())
{
do
{
var entry = CliDB.PlayerDataElementCharacterStorage.LookupByKey(elementsResult.Read<uint>(0));
if (entry == null)
continue;
PlayerDataElement dataElement = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.CharacterDataElements, entry.StorageIndex);
SetUpdateFieldValue(ref dataElement.Type, (uint)entry.Type);
switch (entry.GetElementType())
{
case PlayerDataElementType.Int64:
SetUpdateFieldValue(ref dataElement.Int64Value, elementsResult.Read<long>(1));
break;
case PlayerDataElementType.Float:
SetUpdateFieldValue(ref dataElement.FloatValue, elementsResult.Read<float>(2));
break;
default:
break;
}
} while (elementsResult.NextRow());
}
if (!flagsResult.IsEmpty())
{
BitVectors bitVectors = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.BitVectors);
BitVector bitVector = bitVectors.ModifyValue(bitVectors.Values, (int)PlayerDataFlag.CharacterDataIndex);
do
{
SetUpdateFieldValue(bitVector.ModifyValue(bitVector.Values, flagsResult.Read<int>(0)), flagsResult.Read<ulong>(1));
} while (flagsResult.NextRow());
}
PlayerDataAccount accountData = GetSession().GetPlayerDataAccount();
foreach (var element in accountData.Elements)
{
var entry = CliDB.PlayerDataElementAccountStorage.LookupByKey(element.Id);
if (entry == null)
continue;
PlayerDataElement dataElement = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.AccountDataElements, entry.StorageIndex);
SetUpdateFieldValue(ref dataElement.Type, (uint)entry.Type);
switch (entry.GetElementType())
{
case PlayerDataElementType.Int64:
SetUpdateFieldValue(ref dataElement.Int64Value, element.Int64Value);
break;
case PlayerDataElementType.Float:
SetUpdateFieldValue(ref dataElement.FloatValue, element.FloatValue);
break;
default:
break;
}
}
if (!accountData.Flags.Empty())
{
BitVectors bitVectors = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.BitVectors);
BitVector bitVector = bitVectors.ModifyValue(bitVectors.Values, (int)PlayerDataFlag.AccountDataIndex);
for (var i = 0; i < accountData.Flags.Count; ++i)
SetUpdateFieldValue(bitVector.ModifyValue(bitVector.Values, i), accountData.Flags[i].Value);
}
}
void _LoadCurrency(SQLResult result)
{
if (result.IsEmpty())
@@ -2194,7 +2269,7 @@ namespace Game.Entities
}
// Save spawn trackings
stmt = CharacterDatabase.GetPreparedStatement( CharStatements.DEL_CHAR_QUESTSTATUS_OBJECTIVES_SPAWN_TRACKING_BY_QUEST);
stmt = CharacterDatabase.GetPreparedStatement(CharStatements.DEL_CHAR_QUESTSTATUS_OBJECTIVES_SPAWN_TRACKING_BY_QUEST);
stmt.AddValue(0, GetGUID().GetCounter());
stmt.AddValue(1, save.Key);
trans.Append(stmt);
@@ -2586,6 +2661,7 @@ namespace Game.Entities
}
}
}
void _SaveStats(SQLTransaction trans)
{
// check if stat saving is enabled and if char level is high enough
@@ -2625,6 +2701,71 @@ namespace Game.Entities
trans.Append(stmt);
}
void _SavePlayerData(SQLTransaction trans)
{
ulong guid = GetGUID().GetCounter();
PreparedStatement stmt;
foreach (uint playerDataElementCharacterId in _playerDataElementsNeedSave)
{
stmt = CharacterDatabase.GetPreparedStatement(CharStatements.DEL_PLAYER_DATA_ELEMENTS_CHARACTER);
stmt.AddValue(0, guid);
stmt.AddValue(1, playerDataElementCharacterId);
trans.Append(stmt);
var entry = CliDB.PlayerDataElementCharacterStorage.LookupByKey(playerDataElementCharacterId);
if (entry == null)
continue;
PlayerDataElement element = m_activePlayerData.CharacterDataElements[entry.StorageIndex];
switch (entry.GetElementType())
{
case PlayerDataElementType.Int64:
if (element.Int64Value == 0)
continue;
stmt = CharacterDatabase.GetPreparedStatement(CharStatements.INS_PLAYER_DATA_ELEMENTS_CHARACTER);
stmt.AddValue(0, guid);
stmt.AddValue(1, playerDataElementCharacterId);
stmt.AddNull(2);
stmt.AddValue(3, element.Int64Value);
trans.Append(stmt);
break;
case PlayerDataElementType.Float:
if (element.FloatValue == 0)
continue;
stmt = CharacterDatabase.GetPreparedStatement(CharStatements.INS_PLAYER_DATA_ELEMENTS_CHARACTER);
stmt.AddValue(0, guid);
stmt.AddValue(1, playerDataElementCharacterId);
stmt.AddValue(2, element.FloatValue);
stmt.AddNull(3);
trans.Append(stmt);
break;
}
}
foreach (int storageIndex in _playerDataFlagsNeedSave)
{
stmt = CharacterDatabase.GetPreparedStatement(CharStatements.DEL_PLAYER_DATA_FLAGS_CHARACTER);
stmt.AddValue(0, guid);
stmt.AddValue(1, storageIndex);
trans.Append(stmt);
ulong value = m_activePlayerData.BitVectors.GetValue().Values[(int)PlayerDataFlag.CharacterDataIndex].Values[storageIndex];
if (value == 0)
continue;
stmt = CharacterDatabase.GetPreparedStatement(CharStatements.INS_PLAYER_DATA_FLAGS_CHARACTER);
stmt.AddValue(0, guid);
stmt.AddValue(1, storageIndex);
stmt.AddValue(2, value);
trans.Append(stmt);
}
_playerDataElementsNeedSave.Clear();
_playerDataFlagsNeedSave.Clear();
}
public void SaveInventoryAndGoldToDB(SQLTransaction trans)
{
_SaveInventory(trans);
@@ -2635,6 +2776,7 @@ namespace Game.Entities
stmt.AddValue(1, GetGUID().GetCounter());
trans.Append(stmt);
}
void _SaveEquipmentSets(SQLTransaction trans)
{
foreach (var pair in _equipmentSets)
@@ -3628,6 +3770,8 @@ namespace Game.Entities
_LoadCUFProfiles(holder.GetResult(PlayerLoginQueryLoad.CufProfiles));
_LoadPlayerData(holder.GetResult(PlayerLoginQueryLoad.DataElements), holder.GetResult(PlayerLoginQueryLoad.DataFlags));
var garrison = new Garrison(this);
if (garrison.LoadFromDB(holder.GetResult(PlayerLoginQueryLoad.Garrison),
holder.GetResult(PlayerLoginQueryLoad.GarrisonBlueprints),
@@ -4062,6 +4206,7 @@ namespace Game.Entities
_SaveInstanceTimeRestrictions(characterTransaction);
_SaveCurrency(characterTransaction);
_SaveCUFProfiles(characterTransaction);
_SavePlayerData(characterTransaction);
if (_garrison != null)
_garrison.SaveToDB(characterTransaction);
@@ -4078,6 +4223,7 @@ namespace Game.Entities
GetSession().GetCollectionMgr().SaveAccountItemAppearances(loginTransaction);
GetSession().GetCollectionMgr().SaveAccountTransmogIllusions(loginTransaction);
GetSession().GetCollectionMgr().SaveAccountWarbandScenes(loginTransaction);
GetSession().SavePlayerDataAccount(loginTransaction);
var currentRealmId = Global.RealmMgr.GetCurrentRealmId();
@@ -253,6 +253,9 @@ namespace Game.Entities
PlayerCommandStates _activeCheats;
List<uint> _playerDataElementsNeedSave = new();
List<uint> _playerDataFlagsNeedSave = new();
class ValuesUpdateForPlayerWithMaskSender : IDoWork<Player>
{
Player Owner;
+171 -1
View File
@@ -5027,7 +5027,7 @@ namespace Game.Entities
reward.Money = playerChoiceResponseTemplate.Reward.Money;
reward.Xp = playerChoiceResponseTemplate.Reward.Xp;
void fillRewardItems<T>(List<T> src, List<Networking.Packets.PlayerChoiceResponseRewardEntry> dest)
void fillRewardItems<T>(List<T> src, List<Networking.Packets.PlayerChoiceResponseRewardEntry> dest)
{
for (var j = 0; j < src.Count; ++j)
{
@@ -5077,6 +5077,176 @@ namespace Game.Entities
return ConditionManager.IsPlayerMeetingCondition(this, conditionId);
}
public dynamic GetDataElementAccount(uint dataElementId)
{
var entry = CliDB.PlayerDataElementAccountStorage.LookupByKey(dataElementId);
if (entry == null)
return 0L;
switch (entry.GetElementType())
{
case PlayerDataElementType.Int64:
if (entry.StorageIndex < m_activePlayerData.AccountDataElements.Size())
return m_activePlayerData.AccountDataElements[entry.StorageIndex].Int64Value;
return 0L;
case PlayerDataElementType.Float:
if (entry.StorageIndex < m_activePlayerData.AccountDataElements.Size())
return (0, m_activePlayerData.AccountDataElements[entry.StorageIndex].FloatValue);
return 0.0f;
default:
break;
}
return 0L;
}
public void SetDataElementAccount(uint dataElementId, dynamic value)
{
var entry = CliDB.PlayerDataElementAccountStorage.LookupByKey(dataElementId);
if (entry == null)
return;
PlayerDataElement elementSetter = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.AccountDataElements, entry.StorageIndex);
SetUpdateFieldValue(ref elementSetter.Type, (uint)entry.Type);
switch (entry.GetElementType())
{
case PlayerDataElementType.Int64:
{
long int64Value = value;
SetUpdateFieldValue(ref elementSetter.Int64Value, int64Value);
GetSession().SetPlayerDataElementAccount(dataElementId, int64Value);
break;
}
case PlayerDataElementType.Float:
{
float floatValue = value;
SetUpdateFieldValue(ref elementSetter.FloatValue, floatValue);
GetSession().SetPlayerDataElementAccount(dataElementId, floatValue);
break;
}
default:
break;
}
}
public dynamic GetDataElementCharacter(uint dataElementId)
{
var entry = CliDB.PlayerDataElementCharacterStorage.LookupByKey(dataElementId);
if (entry == null)
return 0L;
switch (entry.GetElementType())
{
case PlayerDataElementType.Int64:
if (entry.StorageIndex < m_activePlayerData.CharacterDataElements.Size())
return m_activePlayerData.CharacterDataElements[entry.StorageIndex].Int64Value;
return 0L;
case PlayerDataElementType.Float:
if (entry.StorageIndex < m_activePlayerData.CharacterDataElements.Size())
return m_activePlayerData.CharacterDataElements[entry.StorageIndex].FloatValue;
return 0.0f;
default:
break;
}
return 0L;
}
public void SetDataElementCharacter(uint dataElementId, dynamic value)
{
var entry = CliDB.PlayerDataElementCharacterStorage.LookupByKey(dataElementId);
if (entry == null)
return;
PlayerDataElement elementSetter = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.CharacterDataElements, entry.StorageIndex);
SetUpdateFieldValue(ref elementSetter.Type, (uint)entry.Type);
switch (entry.GetElementType())
{
case PlayerDataElementType.Int64:
SetUpdateFieldValue(ref elementSetter.Int64Value, value);
break;
case PlayerDataElementType.Float:
SetUpdateFieldValue(ref elementSetter.FloatValue, value);
break;
default:
break;
}
_playerDataElementsNeedSave.Add(dataElementId);
}
public bool HasDataFlagAccount(uint dataFlagId)
{
var entry = CliDB.PlayerDataFlagAccountStorage.LookupByKey(dataFlagId);
if (entry == null)
return false;
int fieldOffset = entry.StorageIndex / PlayerConst.DataFlagValueBits;
ulong flag = 1UL << (entry.StorageIndex % PlayerConst.DataFlagValueBits);
if (fieldOffset >= m_activePlayerData.BitVectors.GetValue().Values[(int)PlayerDataFlag.AccountDataIndex].Values.Size())
return false;
return (m_activePlayerData.BitVectors.GetValue().Values[(int)PlayerDataFlag.AccountDataIndex].Values[fieldOffset] & flag) != 0;
}
public void SetDataFlagAccount(uint dataFlagId, bool on)
{
var entry = CliDB.PlayerDataFlagAccountStorage.LookupByKey(dataFlagId);
if (entry == null)
return;
int fieldOffset = entry.StorageIndex / PlayerConst.DataFlagValueBits;
ulong flag = 1UL << (entry.StorageIndex % PlayerConst.DataFlagValueBits);
BitVectors bitVectors = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.BitVectors);
BitVector bitVector = bitVectors.ModifyValue(bitVectors.Values, (int)PlayerDataFlag.AccountDataIndex);
if (on)
SetUpdateFieldFlagValue(bitVector.ModifyValue(bitVector.Values, fieldOffset), flag);
else
RemoveUpdateFieldFlagValue(bitVector.ModifyValue(bitVector.Values, fieldOffset), flag);
GetSession().SetPlayerDataFlagAccount(dataFlagId, on);
}
public bool HasDataFlagCharacter(uint dataFlagId)
{
var entry = CliDB.PlayerDataFlagCharacterStorage.LookupByKey(dataFlagId);
if (entry == null)
return false;
int fieldOffset = entry.StorageIndex / PlayerConst.DataFlagValueBits;
ulong flag = 1UL << (entry.StorageIndex % PlayerConst.DataFlagValueBits);
if (fieldOffset >= m_activePlayerData.BitVectors.GetValue().Values[(int)PlayerDataFlag.CharacterDataIndex].Values.Size())
return false;
return (m_activePlayerData.BitVectors.GetValue().Values[(int)PlayerDataFlag.CharacterDataIndex].Values[fieldOffset] & flag) != 0;
}
public void SetDataFlagCharacter(uint dataFlagId, bool on)
{
var entry = CliDB.PlayerDataFlagCharacterStorage.LookupByKey(dataFlagId);
if (entry == null)
return;
int fieldOffset = entry.StorageIndex / PlayerConst.DataFlagValueBits;
ulong flag = 1UL << (entry.StorageIndex % PlayerConst.DataFlagValueBits);
BitVectors bitVectors = m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.BitVectors);
BitVector bitVector = bitVectors.ModifyValue(bitVectors.Values, (int)PlayerDataFlag.CharacterDataIndex);
if (on)
SetUpdateFieldFlagValue(bitVector.ModifyValue(bitVector.Values, fieldOffset), flag);
else
RemoveUpdateFieldFlagValue(bitVector.ModifyValue(bitVector.Values, fieldOffset), flag);
_playerDataFlagsNeedSave.Add((uint)fieldOffset);
}
bool IsInFriendlyArea()
{
var areaEntry = CliDB.AreaTableStorage.LookupByKey(GetAreaId());