Core/Transmog: Implemented Transmog Illusions + Spelleffect to unlock them

Port From (https://github.com/TrinityCore/TrinityCore/commit/125ada42f6be220a52315d06d61e472a2ba83395)
This commit is contained in:
hondacrx
2022-06-14 23:07:23 -04:00
parent bf4bf6c321
commit 286294a108
6 changed files with 152 additions and 43 deletions
@@ -170,11 +170,12 @@ namespace Framework.Database
// Transmog collection // Transmog collection
PrepareStatement(LoginStatements.SEL_BNET_ITEM_APPEARANCES, "SELECT blobIndex, appearanceMask FROM battlenet_item_appearances WHERE battlenetAccountId = ? ORDER BY blobIndex DESC"); PrepareStatement(LoginStatements.SEL_BNET_ITEM_APPEARANCES, "SELECT blobIndex, appearanceMask FROM battlenet_item_appearances WHERE battlenetAccountId = ? ORDER BY blobIndex DESC");
PrepareStatement(LoginStatements.INS_BNET_ITEM_APPEARANCES, "INSERT INTO battlenet_item_appearances (battlenetAccountId, blobIndex, appearanceMask) VALUES (?, ?, ?) " + PrepareStatement(LoginStatements.INS_BNET_ITEM_APPEARANCES, "INSERT INTO battlenet_item_appearances (battlenetAccountId, blobIndex, appearanceMask) VALUES (?, ?, ?) ON DUPLICATE KEY UPDATE appearanceMask = appearanceMask | VALUES(appearanceMask)");
"ON DUPLICATE KEY UPDATE appearanceMask = appearanceMask | VALUES(appearanceMask)");
PrepareStatement(LoginStatements.SEL_BNET_ITEM_FAVORITE_APPEARANCES, "SELECT itemModifiedAppearanceId FROM battlenet_item_favorite_appearances WHERE battlenetAccountId = ?"); PrepareStatement(LoginStatements.SEL_BNET_ITEM_FAVORITE_APPEARANCES, "SELECT itemModifiedAppearanceId FROM battlenet_item_favorite_appearances WHERE battlenetAccountId = ?");
PrepareStatement(LoginStatements.INS_BNET_ITEM_FAVORITE_APPEARANCE, "INSERT INTO battlenet_item_favorite_appearances (battlenetAccountId, itemModifiedAppearanceId) VALUES (?, ?)"); PrepareStatement(LoginStatements.INS_BNET_ITEM_FAVORITE_APPEARANCE, "INSERT INTO battlenet_item_favorite_appearances (battlenetAccountId, itemModifiedAppearanceId) VALUES (?, ?)");
PrepareStatement(LoginStatements.DEL_BNET_ITEM_FAVORITE_APPEARANCE, "DELETE FROM battlenet_item_favorite_appearances WHERE battlenetAccountId = ? AND itemModifiedAppearanceId = ?"); PrepareStatement(LoginStatements.DEL_BNET_ITEM_FAVORITE_APPEARANCE, "DELETE FROM battlenet_item_favorite_appearances WHERE battlenetAccountId = ? AND itemModifiedAppearanceId = ?");
PrepareStatement(LoginStatements.SEL_BNET_TRANSMOG_ILLUSIONS, "SELECT blobIndex, illusionMask FROM battlenet_account_transmog_illusions WHERE battlenetAccountId = ? ORDER BY blobIndex DESC");
PrepareStatement(LoginStatements.INS_BNET_TRANSMOG_ILLUSIONS, "INSERT INTO battlenet_account_transmog_illusions (battlenetAccountId, blobIndex, illusionMask) VALUES (?, ?, ?) ON DUPLICATE KEY UPDATE illusionMask = illusionMask | VALUES(illusionMask)");
} }
} }
@@ -318,6 +319,8 @@ namespace Framework.Database
SEL_BNET_ITEM_FAVORITE_APPEARANCES, SEL_BNET_ITEM_FAVORITE_APPEARANCES,
INS_BNET_ITEM_FAVORITE_APPEARANCE, INS_BNET_ITEM_FAVORITE_APPEARANCE,
DEL_BNET_ITEM_FAVORITE_APPEARANCE, DEL_BNET_ITEM_FAVORITE_APPEARANCE,
SEL_BNET_TRANSMOG_ILLUSIONS,
INS_BNET_TRANSMOG_ILLUSIONS,
MAX_LOGINDATABASE_STATEMENTS MAX_LOGINDATABASE_STATEMENTS
} }
+120 -39
View File
@@ -37,6 +37,7 @@ namespace Game.Entities
BitSet _appearances; BitSet _appearances;
MultiMap<uint, ObjectGuid> _temporaryAppearances = new(); MultiMap<uint, ObjectGuid> _temporaryAppearances = new();
Dictionary<uint, FavoriteAppearanceState> _favoriteAppearances = new(); Dictionary<uint, FavoriteAppearanceState> _favoriteAppearances = new();
BitSet _transmogIllusions;
public static void LoadMountDefinitions() public static void LoadMountDefinitions()
{ {
@@ -76,6 +77,7 @@ namespace Game.Entities
{ {
_owner = owner; _owner = owner;
_appearances = new BitSet(0); _appearances = new BitSet(0);
_transmogIllusions = new BitSet(0);
} }
public void LoadToys() public void LoadToys()
@@ -489,7 +491,7 @@ namespace Game.Entities
foreach (uint hiddenItem in hiddenAppearanceItems) foreach (uint hiddenItem in hiddenAppearanceItems)
{ {
ItemModifiedAppearanceRecord hiddenAppearance = Global.DB2Mgr.GetItemModifiedAppearance(hiddenItem, 0); ItemModifiedAppearanceRecord hiddenAppearance = Global.DB2Mgr.GetItemModifiedAppearance(hiddenItem, 0);
//ASSERT(hiddenAppearance); //ASSERT(hiddenAppearance);
if (_appearances.Length <= hiddenAppearance.Id) if (_appearances.Length <= hiddenAppearance.Id)
_appearances.Length = (int)hiddenAppearance.Id + 1; _appearances.Length = (int)hiddenAppearance.Id + 1;
@@ -611,48 +613,48 @@ namespace Game.Entities
switch (itemTemplate.GetClass()) switch (itemTemplate.GetClass())
{ {
case ItemClass.Weapon: case ItemClass.Weapon:
{ {
if (!Convert.ToBoolean(_owner.GetPlayer().GetWeaponProficiency() & (1 << (int)itemTemplate.GetSubClass()))) if (!Convert.ToBoolean(_owner.GetPlayer().GetWeaponProficiency() & (1 << (int)itemTemplate.GetSubClass())))
return false; return false;
if (itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Exotic || if (itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Exotic ||
itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Exotic2 || itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Exotic2 ||
itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Miscellaneous || itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Miscellaneous ||
itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Thrown || itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Thrown ||
itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Spear || itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.Spear ||
itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.FishingPole) itemTemplate.GetSubClass() == (int)ItemSubClassWeapon.FishingPole)
return false; return false;
break; break;
} }
case ItemClass.Armor: case ItemClass.Armor:
{
switch (itemTemplate.GetInventoryType())
{ {
switch (itemTemplate.GetInventoryType()) case InventoryType.Body:
{ case InventoryType.Shield:
case InventoryType.Body: case InventoryType.Cloak:
case InventoryType.Shield: case InventoryType.Tabard:
case InventoryType.Cloak: case InventoryType.Holdable:
case InventoryType.Tabard: break;
case InventoryType.Holdable: case InventoryType.Head:
break; case InventoryType.Shoulders:
case InventoryType.Head: case InventoryType.Chest:
case InventoryType.Shoulders: case InventoryType.Waist:
case InventoryType.Chest: case InventoryType.Legs:
case InventoryType.Waist: case InventoryType.Feet:
case InventoryType.Legs: case InventoryType.Wrists:
case InventoryType.Feet: case InventoryType.Hands:
case InventoryType.Wrists: case InventoryType.Robe:
case InventoryType.Hands: if ((ItemSubClassArmor)itemTemplate.GetSubClass() == ItemSubClassArmor.Miscellaneous)
case InventoryType.Robe:
if ((ItemSubClassArmor)itemTemplate.GetSubClass() == ItemSubClassArmor.Miscellaneous)
return false;
break;
default:
return false; return false;
} break;
if (itemTemplate.GetInventoryType() != InventoryType.Cloak) default:
if (!Convert.ToBoolean(PlayerClassByArmorSubclass[itemTemplate.GetSubClass()] & _owner.GetPlayer().GetClassMask())) return false;
return false;
break;
} }
if (itemTemplate.GetInventoryType() != InventoryType.Cloak)
if (!Convert.ToBoolean(PlayerClassByArmorSubclass[itemTemplate.GetSubClass()] & _owner.GetPlayer().GetClassMask()))
return false;
break;
}
default: default:
return false; return false;
} }
@@ -847,6 +849,85 @@ namespace Game.Entities
return !knownPieces.Contains(0); return !knownPieces.Contains(0);
} }
public void LoadTransmogIllusions()
{
Player owner = _owner.GetPlayer();
foreach (var blockValue in _transmogIllusions.ToBlockRange())
owner.AddIllusionBlock(blockValue);
}
public void LoadAccountTransmogIllusions(SQLResult knownTransmogIllusions)
{
uint[] blocks = new uint[7];
if (!knownTransmogIllusions.IsEmpty())
{
do
{
ushort blobIndex = knownTransmogIllusions.Read<ushort>(0);
if (blobIndex >= blocks.Length)
Array.Resize(ref blocks, blobIndex + 1);
blocks[blobIndex] = knownTransmogIllusions.Read<uint>(1);
} while (knownTransmogIllusions.NextRow());
}
_transmogIllusions = new(blocks);
// Static illusions known by every player
ushort[] defaultIllusions =
{
3, // Lifestealing
13, // Crusader
22, // Striking
23, // Agility
34, // Hide Weapon Enchant
43, // Beastslayer
44, // Titanguard
};
foreach (ushort illusionId in defaultIllusions)
_transmogIllusions.Set(illusionId, true);
}
public void SaveAccountTransmogIllusions(SQLTransaction trans)
{
ushort blockIndex = 0;
foreach (var blockValue in _transmogIllusions.ToBlockRange())
{
if (blockValue != 0) // this table is only appended/bits are set (never cleared) so don't save empty blocks
{
PreparedStatement stmt = DB.Login.GetPreparedStatement(LoginStatements.INS_BNET_TRANSMOG_ILLUSIONS);
stmt.AddValue(0, _owner.GetBattlenetAccountId());
stmt.AddValue(1, blockIndex);
stmt.AddValue(2, blockValue);
trans.Append(stmt);
}
++blockIndex;
}
}
public void AddTransmogIllusion(ushort illusionId)
{
Player owner = _owner.GetPlayer();
if (_transmogIllusions.Count <= illusionId)
{
uint numBlocks = (uint)(_transmogIllusions.Count << 2);
_transmogIllusions.Length = illusionId + 1;
numBlocks = (uint)(_transmogIllusions.Count << 2) - numBlocks;
while (numBlocks-- != 0)
owner.AddIllusionBlock(0);
}
_transmogIllusions.Set(illusionId, true);
int blockIndex = illusionId / 32;
int bitIndex = illusionId % 32;
owner.AddIllusionFlag(blockIndex, (uint)(1 << bitIndex));
}
public bool HasToy(uint itemId) { return _toys.ContainsKey(itemId); } public bool HasToy(uint itemId) { return _toys.ContainsKey(itemId); }
public Dictionary<uint, ToyFlags> GetAccountToys() { return _toys; } public Dictionary<uint, ToyFlags> GetAccountToys() { return _toys; }
public Dictionary<uint, HeirloomData> GetAccountHeirlooms() { return _heirlooms; } public Dictionary<uint, HeirloomData> GetAccountHeirlooms() { return _heirlooms; }
+2
View File
@@ -3135,6 +3135,7 @@ namespace Game.Entities
GetSession().GetCollectionMgr().LoadHeirlooms(); GetSession().GetCollectionMgr().LoadHeirlooms();
GetSession().GetCollectionMgr().LoadMounts(); GetSession().GetCollectionMgr().LoadMounts();
GetSession().GetCollectionMgr().LoadItemAppearances(); GetSession().GetCollectionMgr().LoadItemAppearances();
GetSession().GetCollectionMgr().LoadTransmogIllusions();
LearnSpecializationSpells(); LearnSpecializationSpells();
@@ -3732,6 +3733,7 @@ namespace Game.Entities
GetSession().GetCollectionMgr().SaveAccountHeirlooms(loginTransaction); GetSession().GetCollectionMgr().SaveAccountHeirlooms(loginTransaction);
GetSession().GetCollectionMgr().SaveAccountMounts(loginTransaction); GetSession().GetCollectionMgr().SaveAccountMounts(loginTransaction);
GetSession().GetCollectionMgr().SaveAccountItemAppearances(loginTransaction); GetSession().GetCollectionMgr().SaveAccountItemAppearances(loginTransaction);
GetSession().GetCollectionMgr().SaveAccountTransmogIllusions(loginTransaction);
stmt = DB.Login.GetPreparedStatement(LoginStatements.DEL_BNET_LAST_PLAYER_CHARACTERS); stmt = DB.Login.GetPreparedStatement(LoginStatements.DEL_BNET_LAST_PLAYER_CHARACTERS);
stmt.AddValue(0, GetSession().GetAccountId()); stmt.AddValue(0, GetSession().GetAccountId());
+4
View File
@@ -7721,6 +7721,10 @@ namespace Game.Entities
if (index >= 0) if (index >= 0)
RemoveDynamicUpdateFieldValue(m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.ConditionalTransmog), index); RemoveDynamicUpdateFieldValue(m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.ConditionalTransmog), index);
} }
public void AddIllusionBlock(uint blockValue) { AddDynamicUpdateFieldValue(m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.TransmogIllusions), blockValue); }
public void AddIllusionFlag(int slot, uint flag) { SetUpdateFieldFlagValue(m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.TransmogIllusions, slot), flag); }
public void AddSelfResSpell(uint spellId) { AddDynamicUpdateFieldValue(m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.SelfResSpells), spellId); } public void AddSelfResSpell(uint spellId) { AddDynamicUpdateFieldValue(m_values.ModifyValue(m_activePlayerData).ModifyValue(m_activePlayerData.SelfResSpells), spellId); }
public void RemoveSelfResSpell(uint spellId) public void RemoveSelfResSpell(uint spellId)
{ {
+7 -1
View File
@@ -798,6 +798,7 @@ namespace Game
_collectionMgr.LoadAccountHeirlooms(holder.GetResult(AccountInfoQueryLoad.GlobalAccountHeirlooms)); _collectionMgr.LoadAccountHeirlooms(holder.GetResult(AccountInfoQueryLoad.GlobalAccountHeirlooms));
_collectionMgr.LoadAccountMounts(holder.GetResult(AccountInfoQueryLoad.Mounts)); _collectionMgr.LoadAccountMounts(holder.GetResult(AccountInfoQueryLoad.Mounts));
_collectionMgr.LoadAccountItemAppearances(holder.GetResult(AccountInfoQueryLoad.ItemAppearances), holder.GetResult(AccountInfoQueryLoad.ItemFavoriteAppearances)); _collectionMgr.LoadAccountItemAppearances(holder.GetResult(AccountInfoQueryLoad.ItemAppearances), holder.GetResult(AccountInfoQueryLoad.ItemFavoriteAppearances));
_collectionMgr.LoadAccountTransmogIllusions(holder.GetResult(AccountInfoQueryLoad.TransmogIllusions));
if (!m_inQueue) if (!m_inQueue)
SendAuthResponse(BattlenetRpcErrorCode.Ok, false); SendAuthResponse(BattlenetRpcErrorCode.Ok, false);
@@ -1164,6 +1165,10 @@ namespace Game
stmt = DB.Login.GetPreparedStatement(LoginStatements.SEL_BNET_ITEM_FAVORITE_APPEARANCES); stmt = DB.Login.GetPreparedStatement(LoginStatements.SEL_BNET_ITEM_FAVORITE_APPEARANCES);
stmt.AddValue(0, battlenetAccountId); stmt.AddValue(0, battlenetAccountId);
SetQuery(AccountInfoQueryLoad.ItemFavoriteAppearances, stmt); SetQuery(AccountInfoQueryLoad.ItemFavoriteAppearances, stmt);
stmt = DB.Login.GetPreparedStatement(LoginStatements.SEL_BNET_TRANSMOG_ILLUSIONS);
stmt.AddValue(0, battlenetAccountId);
SetQuery(AccountInfoQueryLoad.TransmogIllusions, stmt);
} }
} }
@@ -1178,6 +1183,7 @@ namespace Game
ItemAppearances, ItemAppearances,
ItemFavoriteAppearances, ItemFavoriteAppearances,
GlobalAccountDataIndexPerRealm, GlobalAccountDataIndexPerRealm,
TutorialsIndexPerRealm TutorialsIndexPerRealm,
TransmogIllusions,
} }
} }
+13
View File
@@ -5655,6 +5655,19 @@ namespace Game.Spells
playerCaster.GetSession().GetBattlePetMgr().GrantBattlePetExperience(unitTarget.GetBattlePetCompanionGUID(), (ushort)damage, BattlePetXpSource.SpellEffect); playerCaster.GetSession().GetBattlePetMgr().GrantBattlePetExperience(unitTarget.GetBattlePetCompanionGUID(), (ushort)damage, BattlePetXpSource.SpellEffect);
} }
[SpellEffectHandler(SpellEffectName.LearnTransmogIllusion)]
void EffectLearnTransmogIllusion()
{
if (effectHandleMode != SpellEffectHandleMode.HitTarget)
return;
Player player = unitTarget?.ToPlayer();
if (player == null)
return;
player.GetSession().GetCollectionMgr().AddTransmogIllusion((ushort)effectInfo.MiscValue);
}
} }
public class DispelableAura public class DispelableAura