Merge branch 'pets' of https://github.com/myran2/TrinityCore into myran2-pets

# Conflicts:
#	src/server/game/Handlers/PetHandler.cpp
#	src/server/game/Handlers/SpellHandler.cpp
#	src/server/game/Server/Packets/PetPackets.cpp
#	src/server/game/Server/Packets/PetPackets.h
#	src/server/game/Server/Protocol/Opcodes.cpp
#	src/server/game/Server/WorldSession.h
This commit is contained in:
DDuarte
2016-03-02 01:38:39 +00:00
parent 397519debf
commit 67b977c86a
12 changed files with 438 additions and 218 deletions
@@ -619,7 +619,7 @@ void CharacterDatabaseConnection::DoPrepareStatements()
// Pet
PrepareStatement(CHAR_SEL_PET_SLOTS, "SELECT owner, slot FROM character_pet WHERE owner = ? AND slot >= ? AND slot <= ? ORDER BY slot", CONNECTION_ASYNC);
PrepareStatement(CHAR_SEL_PET_SLOTS_DETAIL, "SELECT owner, id, entry, level, name FROM character_pet WHERE owner = ? AND slot >= ? AND slot <= ? ORDER BY slot", CONNECTION_ASYNC);
PrepareStatement(CHAR_SEL_PET_SLOTS_DETAIL, "SELECT owner, id, entry, level, name, modelid FROM character_pet WHERE owner = ? AND slot >= ? AND slot <= ? ORDER BY slot", CONNECTION_ASYNC);
PrepareStatement(CHAR_SEL_PET_ENTRY, "SELECT entry FROM character_pet WHERE owner = ? AND id = ? AND slot >= ? AND slot <= ?", CONNECTION_ASYNC);
PrepareStatement(CHAR_SEL_PET_SLOT_BY_ID, "SELECT slot, entry FROM character_pet WHERE owner = ? AND id = ?", CONNECTION_ASYNC);
PrepareStatement(CHAR_SEL_PET_SPELL_LIST, "SELECT DISTINCT pet_spell.spell FROM pet_spell, character_pet WHERE character_pet.owner = ? AND character_pet.id = pet_spell.guid AND character_pet.id <> ?", CONNECTION_SYNCH);
+7 -6
View File
@@ -24,6 +24,7 @@
#include "ObjectMgr.h"
#include "SpellMgr.h"
#include "Pet.h"
#include "PetPackets.h"
#include "SpellAuras.h"
#include "SpellAuraEffects.h"
#include "SpellHistory.h"
@@ -1427,9 +1428,9 @@ bool Pet::learnSpell(uint32 spell_id)
if (!m_loading)
{
WorldPacket data(SMSG_PET_LEARNED_SPELLS, 4);
data << uint32(spell_id);
GetOwner()->GetSession()->SendPacket(&data);
WorldPackets::Pet::PetLearnedSpells packet;
packet.Spells.push_back(spell_id);
GetOwner()->GetSession()->SendPacket(packet.Write());
GetOwner()->PetSpellInitialize();
}
return true;
@@ -1478,9 +1479,9 @@ bool Pet::unlearnSpell(uint32 spell_id, bool learn_prev, bool clear_ab)
{
if (!m_loading)
{
WorldPacket data(SMSG_PET_UNLEARNED_SPELLS, 4);
data << uint32(spell_id);
GetOwner()->GetSession()->SendPacket(&data);
WorldPackets::Pet::PetUnlearnedSpells packet;
packet.Spells.push_back(spell_id);
GetOwner()->GetSession()->SendPacket(packet.Write());
}
return true;
}
+6
View File
@@ -32,6 +32,12 @@ struct PetSpell
PetSpellType type;
};
enum PetStableinfo
{
PET_STABLE_ACTIVE = 1,
PET_STABLE_INACTIVE = 2
};
typedef std::unordered_map<uint32, PetSpell> PetSpellMap;
typedef std::vector<uint32> AutoSpellList;
+23 -36
View File
@@ -74,6 +74,7 @@
#include "OutdoorPvP.h"
#include "OutdoorPvPMgr.h"
#include "Pet.h"
#include "PetPackets.h"
#include "QuestDef.h"
#include "QuestPackets.h"
#include "ReputationMgr.h"
@@ -19958,9 +19959,8 @@ void Player::RemovePet(Pet* pet, PetSaveMode mode, bool returnreagent)
if (pet->isControlled())
{
WorldPacket data(SMSG_PET_SPELLS_MESSAGE, 8);
data << uint64(0);
GetSession()->SendPacket(&data);
WorldPackets::Pet::PetSpells petSpellsPacket;
GetSession()->SendPacket(petSpellsPacket.Write());
if (GetGroup())
SetGroupUpdateFlag(GROUP_UPDATE_FLAG_PET);
@@ -20107,22 +20107,17 @@ void Player::PetSpellInitialize()
CharmInfo* charmInfo = pet->GetCharmInfo();
WorldPacket data(SMSG_PET_SPELLS_MESSAGE, 8 + 2 + 4 + 4 + 4 * MAX_UNIT_ACTION_BAR_INDEX + 1 + 1);
data << pet->GetGUID();
data << uint16(pet->GetCreatureTemplate()->family); // creature family (required for pet talents)
data << uint32(pet->GetDuration());
data << uint8(pet->GetReactState());
data << uint8(charmInfo->GetCommandState());
data << uint16(0); // Flags, mostly unknown
WorldPackets::Pet::PetSpells petSpellsPacket;
petSpellsPacket.PetGUID = pet->GetGUID();
petSpellsPacket.CreatureFamily = pet->GetCreatureTemplate()->family; // creature family (required for pet talents)
//petSpellsPacket.Specialization = pet->GetSpecialization(); NYI
petSpellsPacket.TimeLimit = pet->GetDuration();
petSpellsPacket.ReactState = pet->GetReactState();
petSpellsPacket.CommandState = charmInfo->GetCommandState();
// action bar loop
charmInfo->BuildActionBar(&data);
size_t spellsCountPos = data.wpos();
// spells count
uint8 addlist = 0;
data << uint8(addlist); // placeholder
for (uint32 i = 0; i < MAX_UNIT_ACTION_BAR_INDEX; ++i)
petSpellsPacket.ActionButtons[i] = charmInfo->GetActionBarEntry(i)->packedData;
if (pet->IsPermanentPetFor(this))
{
@@ -20132,17 +20127,14 @@ void Player::PetSpellInitialize()
if (itr->second.state == PETSPELL_REMOVED)
continue;
data << uint32(MAKE_UNIT_ACTION_BUTTON(itr->first, itr->second.active));
++addlist;
petSpellsPacket.Actions.push_back(MAKE_UNIT_ACTION_BUTTON(itr->first, itr->second.active));
}
}
data.put<uint8>(spellsCountPos, addlist);
// Cooldowns
//pet->GetSpellHistory()->WritePacket(&petSpells);
pet->GetSpellHistory()->WritePacket(&petSpellsPacket);
GetSession()->SendPacket(&data);
GetSession()->SendPacket(petSpellsPacket.Write());
}
void Player::PossessSpellInitialize()
@@ -20159,20 +20151,16 @@ void Player::PossessSpellInitialize()
return;
}
WorldPacket data(SMSG_PET_SPELLS_MESSAGE, 8 + 2 + 4 + 4 + 4 * MAX_UNIT_ACTION_BAR_INDEX + 1 + 1);
data << charm->GetGUID();
data << uint16(0);
data << uint32(0);
data << uint32(0);
WorldPackets::Pet::PetSpells petSpellsPacket;
petSpellsPacket.PetGUID = charm->GetGUID();
charmInfo->BuildActionBar(&data);
data << uint8(0); // spells count
for (uint32 i = 0; i < MAX_UNIT_ACTION_BAR_INDEX; ++i)
petSpellsPacket.ActionButtons[i] = charmInfo->GetActionBarEntry(i)->packedData;
// Cooldowns
//charm->GetSpellHistory()->WritePacket(&petSpells);
charm->GetSpellHistory()->WritePacket(&petSpellsPacket);
GetSession()->SendPacket(&data);
GetSession()->SendPacket(petSpellsPacket.Write());
}
void Player::VehicleSpellInitialize()
@@ -20284,9 +20272,8 @@ void Player::CharmSpellInitialize()
void Player::SendRemoveControlBar() const
{
WorldPacket data(SMSG_PET_SPELLS_MESSAGE, 8);
data << uint64(0);
GetSession()->SendPacket(&data);
WorldPackets::Pet::PetSpells packet;
GetSession()->SendPacket(packet.Write());
}
bool Player::IsAffectedBySpellmod(SpellInfo const* spellInfo, SpellModifier* mod, Spell* spell) const
+26 -26
View File
@@ -31,6 +31,7 @@
#include "ObjectAccessor.h"
#include "Creature.h"
#include "Pet.h"
#include "PetPackets.h"
#include "ReputationMgr.h"
#include "BattlegroundMgr.h"
#include "Battleground.h"
@@ -496,29 +497,27 @@ void WorldSession::SendStablePetCallback(PreparedQueryResult result, ObjectGuid
if (!GetPlayer())
return;
WorldPacket data(SMSG_PET_STABLE_LIST, 200); // guess size
WorldPackets::Pet::PetStableList packet;
data << guid;
packet.StableMaster = guid;
Pet* pet = _player->GetPet();
size_t wpos = data.wpos();
data << uint8(0); // place holder for slot show number
data << uint8(GetPlayer()->m_stableSlots);
uint8 num = 0; // counter for place holder
int32 petSlot = 0;
// not let move dead pet in slot
if (pet && pet->IsAlive() && pet->getPetType() == HUNTER_PET)
{
data << uint32(num); // 4.x unknown, some kind of order?
data << uint32(pet->GetCharmInfo()->GetPetNumber());
data << uint32(pet->GetEntry());
data << uint32(pet->getLevel());
data << pet->GetName(); // petname
data << uint8(1); // 1 = current, 2/3 = in stable (any from 4, 5, ... create problems with proper show)
++num;
WorldPackets::Pet::PetStableInfo stableEntry;
stableEntry.PetSlot = petSlot;
stableEntry.PetNumber = pet->GetCharmInfo()->GetPetNumber();
stableEntry.CreatureID = pet->GetEntry();
stableEntry.DisplayID = pet->GetDisplayId();
stableEntry.ExperienceLevel = pet->getLevel();
stableEntry.PetFlags = PET_STABLE_ACTIVE;
stableEntry.PetName = pet->GetName();
++petSlot;
packet.Pets.push_back(stableEntry);
}
if (result)
@@ -526,22 +525,23 @@ void WorldSession::SendStablePetCallback(PreparedQueryResult result, ObjectGuid
do
{
Field* fields = result->Fetch();
WorldPackets::Pet::PetStableInfo stableEntry;
data << uint32(num);
data << uint32(fields[1].GetUInt32()); // petnumber
data << uint32(fields[2].GetUInt32()); // creature entry
data << uint32(fields[3].GetUInt16()); // level
data << fields[4].GetString(); // name
data << uint8(2); // 1 = current, 2/3 = in stable (any from 4, 5, ... create problems with proper show)
stableEntry.PetSlot = petSlot;
stableEntry.PetNumber = fields[1].GetUInt32(); // petnumber
stableEntry.CreatureID = fields[2].GetUInt32(); // creature entry
stableEntry.DisplayID = fields[5].GetUInt32(); // creature displayid
stableEntry.ExperienceLevel = fields[3].GetUInt16(); // level
stableEntry.PetFlags = PET_STABLE_INACTIVE;
stableEntry.PetName = fields[4].GetString(); // Name
++num;
++petSlot;
packet.Pets.push_back(stableEntry);
}
while (result->NextRow());
}
data.put<uint8>(wpos, num); // set real data to placeholder
SendPacket(&data);
SendPacket(packet.Write());
}
void WorldSession::SendPetStableResult(uint8 res)
+51 -127
View File
@@ -28,6 +28,7 @@
#include "CreatureAI.h"
#include "Util.h"
#include "Pet.h"
#include "PetPackets.h"
#include "World.h"
#include "Group.h"
#include "SpellHistory.h"
@@ -59,22 +60,13 @@ void WorldSession::HandleRequestPetInfo(WorldPackets::Pet::RequestPetInfo& /*pac
{
}
void WorldSession::HandlePetAction(WorldPacket& recvData)
void WorldSession::HandlePetAction(WorldPackets::Pet::PetAction& packet)
{
ObjectGuid guid1;
uint32 data;
ObjectGuid guid2;
float x, y, z;
recvData >> guid1; //pet guid
recvData >> data;
recvData >> guid2; //tag guid
// Position
recvData >> x;
recvData >> y;
recvData >> z;
ObjectGuid guid1 = packet.PetGUID; //pet guid
ObjectGuid guid2 = packet.TargetGUID; //tag guid
uint32 spellid = UNIT_ACTION_BUTTON_ACTION(data);
uint8 flag = UNIT_ACTION_BUTTON_TYPE(data); //delete = 0x07 CastSpell = C1
uint32 spellid = UNIT_ACTION_BUTTON_ACTION(packet.Action);
uint8 flag = UNIT_ACTION_BUTTON_TYPE(packet.Action); //delete = 0x07 CastSpell = C1
// used also for charmed creature
Unit* pet = ObjectAccessor::GetUnit(*_player, guid1);
@@ -106,7 +98,7 @@ void WorldSession::HandlePetAction(WorldPacket& recvData)
return;
if (GetPlayer()->m_Controlled.size() == 1)
HandlePetActionHelper(pet, guid1, spellid, flag, guid2, x, y, z);
HandlePetActionHelper(pet, guid1, spellid, flag, guid2, packet.ActionPosition.x, packet.ActionPosition.y, packet.ActionPosition.z);
else
{
//If a pet is dismissed, m_Controlled will change
@@ -115,7 +107,7 @@ void WorldSession::HandlePetAction(WorldPacket& recvData)
if ((*itr)->GetEntry() == pet->GetEntry() && (*itr)->IsAlive())
controlled.push_back(*itr);
for (std::vector<Unit*>::iterator itr = controlled.begin(); itr != controlled.end(); ++itr)
HandlePetActionHelper(*itr, guid1, spellid, flag, guid2, x, y, z);
HandlePetActionHelper(*itr, guid1, spellid, flag, guid2, packet.ActionPosition.x, packet.ActionPosition.y, packet.ActionPosition.z);
}
}
@@ -462,13 +454,9 @@ bool WorldSession::CheckStableMaster(ObjectGuid guid)
return true;
}
void WorldSession::HandlePetSetAction(WorldPacket& recvData)
void WorldSession::HandlePetSetAction(WorldPackets::Pet::PetSetAction& packet)
{
ObjectGuid petguid;
uint8 count;
recvData >> petguid;
ObjectGuid petguid = packet.PetGUID;
Unit* pet = ObjectAccessor::GetUnit(*_player, petguid);
if (!pet || pet != _player->GetFirstControlled())
@@ -484,110 +472,53 @@ void WorldSession::HandlePetSetAction(WorldPacket& recvData)
return;
}
count = (recvData.size() == 24) ? 2 : 1;
uint32 position = packet.Index;
uint32 actionData = packet.Action;
uint32 position[2];
uint32 data[2];
bool move_command = false;
uint32 spell_id = UNIT_ACTION_BUTTON_ACTION(actionData);
uint8 act_state = UNIT_ACTION_BUTTON_TYPE(actionData);
for (uint8 i = 0; i < count; ++i)
TC_LOG_DEBUG("network", "Player %s has changed pet spell action. Position: %u, Spell: %u, State: 0x%X",
_player->GetName().c_str(), position, spell_id, uint32(act_state));
//if it's act for spell (en/disable/cast) and there is a spell given (0 = remove spell) which pet doesn't know, don't add
if (!((act_state == ACT_ENABLED || act_state == ACT_DISABLED || act_state == ACT_PASSIVE) && spell_id && !pet->HasSpell(spell_id)))
{
recvData >> position[i];
recvData >> data[i];
uint8 act_state = UNIT_ACTION_BUTTON_TYPE(data[i]);
//ignore invalid position
if (position[i] >= MAX_UNIT_ACTION_BAR_INDEX)
return;
// in the normal case, command and reaction buttons can only be moved, not removed
// at moving count == 2, at removing count == 1
// ignore attempt to remove command|reaction buttons (not possible at normal case)
if (act_state == ACT_COMMAND || act_state == ACT_REACTION)
if (SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spell_id))
{
if (count == 1)
return;
move_command = true;
}
}
// check swap (at command->spell swap client remove spell first in another packet, so check only command move correctness)
if (move_command)
{
uint8 act_state_0 = UNIT_ACTION_BUTTON_TYPE(data[0]);
if (act_state_0 == ACT_COMMAND || act_state_0 == ACT_REACTION)
{
uint32 spell_id_0 = UNIT_ACTION_BUTTON_ACTION(data[0]);
UnitActionBarEntry const* actionEntry_1 = charmInfo->GetActionBarEntry(position[1]);
if (!actionEntry_1 || spell_id_0 != actionEntry_1->GetAction() ||
act_state_0 != actionEntry_1->GetType())
return;
}
uint8 act_state_1 = UNIT_ACTION_BUTTON_TYPE(data[1]);
if (act_state_1 == ACT_COMMAND || act_state_1 == ACT_REACTION)
{
uint32 spell_id_1 = UNIT_ACTION_BUTTON_ACTION(data[1]);
UnitActionBarEntry const* actionEntry_0 = charmInfo->GetActionBarEntry(position[0]);
if (!actionEntry_0 || spell_id_1 != actionEntry_0->GetAction() ||
act_state_1 != actionEntry_0->GetType())
return;
}
}
for (uint8 i = 0; i < count; ++i)
{
uint32 spell_id = UNIT_ACTION_BUTTON_ACTION(data[i]);
uint8 act_state = UNIT_ACTION_BUTTON_TYPE(data[i]);
TC_LOG_DEBUG("network", "Player %s has changed pet spell action. Position: %u, Spell: %u, State: 0x%X",
_player->GetName().c_str(), position[i], spell_id, uint32(act_state));
//if it's act for spell (en/disable/cast) and there is a spell given (0 = remove spell) which pet doesn't know, don't add
if (!((act_state == ACT_ENABLED || act_state == ACT_DISABLED || act_state == ACT_PASSIVE) && spell_id && !pet->HasSpell(spell_id)))
{
if (SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spell_id))
//sign for autocast
if (act_state == ACT_ENABLED)
{
//sign for autocast
if (act_state == ACT_ENABLED)
{
if (pet->GetTypeId() == TYPEID_UNIT && pet->IsPet())
((Pet*)pet)->ToggleAutocast(spellInfo, true);
else
for (Unit::ControlList::iterator itr = GetPlayer()->m_Controlled.begin(); itr != GetPlayer()->m_Controlled.end(); ++itr)
if ((*itr)->GetEntry() == pet->GetEntry())
(*itr)->GetCharmInfo()->ToggleCreatureAutocast(spellInfo, true);
}
//sign for no/turn off autocast
else if (act_state == ACT_DISABLED)
{
if (pet->GetTypeId() == TYPEID_UNIT && pet->IsPet())
((Pet*)pet)->ToggleAutocast(spellInfo, false);
else
for (Unit::ControlList::iterator itr = GetPlayer()->m_Controlled.begin(); itr != GetPlayer()->m_Controlled.end(); ++itr)
if ((*itr)->GetEntry() == pet->GetEntry())
(*itr)->GetCharmInfo()->ToggleCreatureAutocast(spellInfo, false);
}
if (pet->GetTypeId() == TYPEID_UNIT && pet->IsPet())
((Pet*)pet)->ToggleAutocast(spellInfo, true);
else
for (Unit::ControlList::iterator itr = GetPlayer()->m_Controlled.begin(); itr != GetPlayer()->m_Controlled.end(); ++itr)
if ((*itr)->GetEntry() == pet->GetEntry())
(*itr)->GetCharmInfo()->ToggleCreatureAutocast(spellInfo, true);
}
//sign for no/turn off autocast
else if (act_state == ACT_DISABLED)
{
if (pet->GetTypeId() == TYPEID_UNIT && pet->IsPet())
((Pet*)pet)->ToggleAutocast(spellInfo, false);
else
for (Unit::ControlList::iterator itr = GetPlayer()->m_Controlled.begin(); itr != GetPlayer()->m_Controlled.end(); ++itr)
if ((*itr)->GetEntry() == pet->GetEntry())
(*itr)->GetCharmInfo()->ToggleCreatureAutocast(spellInfo, false);
}
charmInfo->SetActionBar(position[i], spell_id, ActiveStates(act_state));
}
charmInfo->SetActionBar(position, spell_id, ActiveStates(act_state));
}
}
void WorldSession::HandlePetRename(WorldPacket& recvData)
void WorldSession::HandlePetRename(WorldPackets::Pet::PetRename& packet)
{
ObjectGuid petguid;
uint8 isdeclined;
ObjectGuid petguid = packet.RenameData.PetGUID;
bool isdeclined = packet.RenameData.HasDeclinedNames;
std::string name;
DeclinedName declinedname;
recvData >> petguid;
recvData >> name;
recvData >> isdeclined;
std::string name = packet.RenameData.NewName;
DeclinedName declinedname = packet.RenameData.DeclinedNames;
Pet* pet = ObjectAccessor::GetPet(*_player, petguid);
// check it!
@@ -617,11 +548,6 @@ void WorldSession::HandlePetRename(WorldPacket& recvData)
if (isdeclined)
{
for (uint8 i = 0; i < MAX_DECLINED_NAME_CASES; ++i)
{
recvData >> declinedname.name[i];
}
std::wstring wname;
if (!Utf8toWStr(name, wname))
return;
@@ -788,13 +714,11 @@ void WorldSession::HandlePetCastSpellOpcode(WorldPackets::Spells::PetCastSpell&
void WorldSession::SendPetNameInvalid(uint32 error, const std::string& name, DeclinedName *declinedName)
{
WorldPacket data(SMSG_PET_NAME_INVALID, 4 + name.size() + 1 + 1);
data << uint32(error);
data << name;
data << uint8(declinedName ? 1 : 0);
if (declinedName)
for (uint32 i = 0; i < MAX_DECLINED_NAME_CASES; ++i)
data << declinedName->name[i];
WorldPackets::Pet::PetNameInvalid petNameInvalid;
petNameInvalid.Result = error;
petNameInvalid.RenameData.NewName = name;
for (int i = 0; i < MAX_DECLINED_NAME_CASES; i++)
petNameInvalid.RenameData.DeclinedNames.name[i] = declinedName[i].name[i];
SendPacket(&data);
SendPacket(petNameInvalid.Write());
}
@@ -52,6 +52,7 @@
#include "PartyPackets.h"
#include "PetPackets.h"
#include "PetitionPackets.h"
#include "PetPackets.h"
#include "QueryPackets.h"
#include "QuestPackets.h"
#include "ReferAFriendPackets.h"
+151 -4
View File
@@ -17,14 +17,137 @@
#include "PetPackets.h"
void WorldPackets::Pet::DismissCritter::Read()
WorldPacket const* WorldPackets::Pet::PetSpells::Write()
{
_worldPacket >> CritterGUID;
_worldPacket << PetGUID;
_worldPacket << int16(CreatureFamily);
_worldPacket << int16(Specialization);
_worldPacket << int32(TimeLimit);
uint32 petModeAndOrders = ReactState + (CommandState << 8) + (Flag << 16);
_worldPacket << uint32(petModeAndOrders);
for (uint32 actionButton : ActionButtons)
_worldPacket << int32(actionButton);
_worldPacket << int32(Actions.size());
_worldPacket << int32(Cooldowns.size());
_worldPacket << int32(SpellHistory.size());
for (uint32 action : Actions)
_worldPacket << action;
for (PetSpellCooldown const& cooldown : Cooldowns)
{
_worldPacket << int32(cooldown.SpellID);
_worldPacket << int32(cooldown.Duration);
_worldPacket << int32(cooldown.CategoryDuration);
_worldPacket << int16(cooldown.Category);
}
for (PetSpellHistory const& history : SpellHistory)
{
_worldPacket << int32(history.CategoryID);
_worldPacket << int32(history.RecoveryTime);
_worldPacket << int8(history.ConsumedCharges);
}
return &_worldPacket;
}
void WorldPackets::Pet::PetAbandon::Read()
WorldPacket const* WorldPackets::Pet::PetStableList::Write()
{
_worldPacket >> Pet;
_worldPacket << StableMaster;
_worldPacket << uint32(Pets.size());
for (PetStableInfo const& pet : Pets)
{
_worldPacket << int32(pet.PetSlot);
_worldPacket << int32(pet.PetNumber);
_worldPacket << int32(pet.CreatureID);
_worldPacket << int32(pet.DisplayID);
_worldPacket << int32(pet.ExperienceLevel);
_worldPacket << int32(pet.PetFlags);
_worldPacket << int8(pet.PetName.length());
_worldPacket.WriteString(pet.PetName);
}
return &_worldPacket;
}
WorldPacket const* WorldPackets::Pet::PetLearnedSpells::Write()
{
_worldPacket << uint32(Spells.size());
for (uint32 spell : Spells)
_worldPacket << int32(spell);
return &_worldPacket;
}
WorldPacket const* WorldPackets::Pet::PetUnlearnedSpells::Write()
{
_worldPacket << uint32(Spells.size());
for (uint32 spell : Spells)
_worldPacket << int32(spell);
return &_worldPacket;
}
WorldPacket const* WorldPackets::Pet::PetNameInvalid::Write()
{
_worldPacket << RenameData.PetGUID;
_worldPacket << int32(RenameData.PetNumber);
_worldPacket << uint8(RenameData.NewName.length());
_worldPacket.WriteBit(RenameData.HasDeclinedNames);
_worldPacket.FlushBits();
if (RenameData.HasDeclinedNames)
{
for (int32 i = 0; i < MAX_DECLINED_NAME_CASES; i++)
{
_worldPacket.WriteBits(RenameData.DeclinedNames.name[i].length(), 7);
_worldPacket.FlushBits();
}
for (int32 i = 0; i < MAX_DECLINED_NAME_CASES; i++)
_worldPacket << RenameData.DeclinedNames.name[i];
}
_worldPacket.WriteString(RenameData.NewName);
return &_worldPacket;
}
void WorldPackets::Pet::PetRename::Read()
{
_worldPacket >> RenameData.PetGUID;
_worldPacket >> RenameData.PetNumber;
int8 nameLen = 0;
_worldPacket >> nameLen;
RenameData.HasDeclinedNames = _worldPacket.ReadBit();
if (RenameData.HasDeclinedNames)
{
int32 count[MAX_DECLINED_NAME_CASES];
for (int32 i = 0; i < MAX_DECLINED_NAME_CASES; i++)
count[i] = _worldPacket.ReadBits(7);
for (int32 i = 0; i < MAX_DECLINED_NAME_CASES; i++)
RenameData.DeclinedNames.name[i] = _worldPacket.ReadString(count[i]);
}
RenameData.NewName = _worldPacket.ReadString(nameLen);
}
void WorldPackets::Pet::PetAction::Read()
{
_worldPacket >> PetGUID;
_worldPacket >> Action;
_worldPacket >> TargetGUID;
_worldPacket >> ActionPosition;
}
void WorldPackets::Pet::PetStopAttack::Read()
@@ -32,9 +155,33 @@ void WorldPackets::Pet::PetStopAttack::Read()
_worldPacket >> PetGUID;
}
void WorldPackets::Pet::PetSetAction::Read()
{
_worldPacket >> PetGUID;
_worldPacket >> Index;
_worldPacket >> Action;
}
void WorldPackets::Pet::PetAbandon::Read()
{
_worldPacket >> PetGUID;
}
void WorldPackets::Pet::PetSpellAutocast::Read()
{
_worldPacket >> PetGUID;
_worldPacket >> SpellID;
AutocastEnabled = _worldPacket.ReadBit();
}
void WorldPackets::Pet::DismissCritter::Read()
{
_worldPacket >> CritterGUID;
}
void WorldPackets::Pet::PetCancelAura::Read()
{
_worldPacket >> PetGUID;
_worldPacket >> SpellID;
}
+154 -3
View File
@@ -20,6 +20,8 @@
#include "Packet.h"
#include "ObjectGuid.h"
#include "Unit.h"
#include "WorldSession.h"
namespace WorldPackets
{
@@ -39,7 +41,7 @@ namespace WorldPackets
{
public:
RequestPetInfo(WorldPacket&& packet) : ClientPacket(CMSG_REQUEST_PET_INFO, std::move(packet)) { }
void Read() override { }
};
@@ -57,7 +59,7 @@ namespace WorldPackets
{
public:
PetStopAttack(WorldPacket&& packet) : ClientPacket(CMSG_PET_STOP_ATTACK, std::move(packet)) { }
void Read() override;
ObjectGuid PetGUID;
@@ -67,13 +69,162 @@ namespace WorldPackets
{
public:
PetSpellAutocast(WorldPacket&& packet) : ClientPacket(CMSG_PET_SPELL_AUTOCAST, std::move(packet)) { }
void Read() override;
ObjectGuid PetGUID;
uint32 SpellID = 0;
bool AutocastEnabled = false;
};
struct PetSpellCooldown
{
int32 SpellID = 0;
int32 Duration = 0;
int32 CategoryDuration = 0;
int Category = 0;
};
struct PetSpellHistory
{
int32 CategoryID = 0;
int32 RecoveryTime = 0;
int8 ConsumedCharges = 0;
};
class PetSpells final : public ServerPacket
{
public:
PetSpells() : ServerPacket(SMSG_PET_SPELLS_MESSAGE, 100) { }
WorldPacket const* Write() override;
ObjectGuid PetGUID;
uint16 CreatureFamily = 0;
uint16 Specialization = 0;
uint32 TimeLimit = 0;
uint8 ReactState = 0;
uint8 CommandState = 0;
uint16 Flag = 0;
std::array<int, 10> ActionButtons;
std::vector<uint32> Actions;
std::vector<PetSpellCooldown> Cooldowns;
std::vector<PetSpellHistory> SpellHistory;
};
struct PetStableInfo
{
uint32 PetSlot = 0;
uint32 PetNumber = 0;
uint32 CreatureID = 0;
uint32 DisplayID = 0;
uint32 ExperienceLevel = 0;
uint32 PetFlags = 0;
std::string PetName;
};
class PetStableList final : public ServerPacket
{
public:
PetStableList() : ServerPacket(SMSG_PET_STABLE_LIST, 18 + 2) { }
WorldPacket const* Write() override;
ObjectGuid StableMaster;
std::vector<PetStableInfo> Pets;
};
class PetLearnedSpells final : public ServerPacket
{
public:
PetLearnedSpells() : ServerPacket(SMSG_PET_LEARNED_SPELLS, 4) { }
WorldPacket const* Write() override;
std::vector<uint32> Spells;
};
class PetUnlearnedSpells final : public ServerPacket
{
public:
PetUnlearnedSpells() : ServerPacket(SMSG_PET_UNLEARNED_SPELLS, 4) { }
WorldPacket const* Write() override;
std::vector<uint32> Spells;
};
struct PetRenameData
{
ObjectGuid PetGUID;
int32 PetNumber = 0;
std::string NewName;
bool HasDeclinedNames = false;
DeclinedName DeclinedNames;
};
class PetNameInvalid final : public ServerPacket
{
public:
PetNameInvalid() : ServerPacket(SMSG_PET_NAME_INVALID, 18 + 4 + 2 + 1 + 5 * 2 + 2) { }
WorldPacket const* Write() override;
PetRenameData RenameData;
uint8 Result = 0;
};
class PetRename final : public ClientPacket
{
public:
PetRename(WorldPacket&& packet) : ClientPacket(CMSG_PET_RENAME, std::move(packet)) { }
void Read() override;
PetRenameData RenameData;
};
class PetAction final : public ClientPacket
{
public:
PetAction(WorldPacket&& packet) : ClientPacket(CMSG_PET_ACTION, std::move(packet)) { }
void Read() override;
ObjectGuid PetGUID;
uint32 Action = 0;
ObjectGuid TargetGUID;
G3D::Vector3 ActionPosition;
};
class PetSetAction final : public ClientPacket
{
public:
PetSetAction(WorldPacket&& packet) : ClientPacket(CMSG_PET_SET_ACTION, std::move(packet)) { }
void Read() override;
ObjectGuid PetGUID;
uint32 Index = 0;
uint32 Action = 0;
};
class PetCancelAura final : public ClientPacket
{
public:
PetCancelAura(WorldPacket&& packet) : ClientPacket(CMSG_PET_CANCEL_AURA, std::move(packet)) { }
void Read() override;
ObjectGuid PetGUID;
int32 SpellID = 0;
};
}
}
+7 -7
View File
@@ -558,7 +558,7 @@ void OpcodeTable::Initialize()
DEFINE_HANDLER(CMSG_PETITION_SHOW_LIST, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Petition::PetitionShowList, &WorldSession::HandlePetitionShowList);
DEFINE_HANDLER(CMSG_PETITION_SHOW_SIGNATURES, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Petition::PetitionShowSignatures, &WorldSession::HandlePetitionShowSignatures);
DEFINE_HANDLER(CMSG_PET_ABANDON, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Pet::PetAbandon ,&WorldSession::HandlePetAbandon);
DEFINE_OPCODE_HANDLER_OLD(CMSG_PET_ACTION, STATUS_UNHANDLED, PROCESS_THREADUNSAFE, &WorldSession::HandlePetAction );
DEFINE_HANDLER(CMSG_PET_ACTION, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Pet::PetAction, &WorldSession::HandlePetAction);
DEFINE_HANDLER(CMSG_PET_BATTLE_FINAL_NOTIFY, STATUS_UNHANDLED, PROCESS_INPLACE, WorldPackets::Null, &WorldSession::Handle_NULL);
DEFINE_HANDLER(CMSG_PET_BATTLE_INPUT, STATUS_UNHANDLED, PROCESS_INPLACE, WorldPackets::Null, &WorldSession::Handle_NULL);
DEFINE_HANDLER(CMSG_PET_BATTLE_QUEUE_PROPOSE_MATCH_RESULT, STATUS_UNHANDLED, PROCESS_INPLACE, WorldPackets::Null, &WorldSession::Handle_NULL);
@@ -570,8 +570,8 @@ void OpcodeTable::Initialize()
DEFINE_HANDLER(CMSG_PET_BATTLE_SCRIPT_ERROR_NOTIFY, STATUS_UNHANDLED, PROCESS_INPLACE, WorldPackets::Null, &WorldSession::Handle_NULL);
DEFINE_HANDLER(CMSG_PET_CANCEL_AURA, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Spells::PetCancelAura, &WorldSession::HandlePetCancelAuraOpcode);
DEFINE_HANDLER(CMSG_PET_CAST_SPELL, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Spells::PetCastSpell, &WorldSession::HandlePetCastSpellOpcode);
DEFINE_OPCODE_HANDLER_OLD(CMSG_PET_RENAME, STATUS_UNHANDLED, PROCESS_THREADUNSAFE, &WorldSession::HandlePetRename );
DEFINE_OPCODE_HANDLER_OLD(CMSG_PET_SET_ACTION, STATUS_UNHANDLED, PROCESS_THREADUNSAFE, &WorldSession::HandlePetSetAction );
DEFINE_HANDLER(CMSG_PET_RENAME, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Pet::PetRename, &WorldSession::HandlePetRename);
DEFINE_HANDLER(CMSG_PET_SET_ACTION, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Pet::PetSetAction, &WorldSession::HandlePetSetAction );
DEFINE_HANDLER(CMSG_PET_SPELL_AUTOCAST, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Pet::PetSpellAutocast, &WorldSession::HandlePetSpellAutocastOpcode);
DEFINE_HANDLER(CMSG_PET_STOP_ATTACK, STATUS_LOGGEDIN, PROCESS_THREADUNSAFE, WorldPackets::Pet::PetStopAttack, &WorldSession::HandlePetStopAttack);
DEFINE_HANDLER(CMSG_PING, STATUS_UNHANDLED, PROCESS_INPLACE, WorldPacket, &WorldSession::Handle_EarlyProccess);
@@ -1427,15 +1427,15 @@ void OpcodeTable::Initialize()
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_DISMISS_SOUND, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_GOD_MODE, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_GUIDS, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_LEARNED_SPELLS, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_LEARNED_SPELLS, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_MODE, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_NAME_INVALID, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_SLOT_UPDATED, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_SPELLS_MESSAGE, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_STABLE_LIST, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_SPELLS_MESSAGE, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_STABLE_LIST, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_STABLE_RESULT, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_TAME_FAILURE, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_UNLEARNED_SPELLS, STATUS_UNHANDLED, CONNECTION_TYPE_REALM);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PET_UNLEARNED_SPELLS, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PHASE_SHIFT_CHANGE, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PLAYED_TIME, STATUS_NEVER, CONNECTION_TYPE_INSTANCE);
DEFINE_SERVER_OPCODE_HANDLER(SMSG_PLAYER_BOUND, STATUS_NEVER, CONNECTION_TYPE_REALM);
+7 -3
View File
@@ -490,6 +490,10 @@ namespace WorldPackets
class PetAbandon;
class PetStopAttack;
class PetSpellAutocast;
class PetRename;
class PetAction;
class PetCancelAura;
class PetSetAction;
}
namespace Petition
@@ -1472,13 +1476,13 @@ class WorldSession
void HandleTutorialFlag(WorldPackets::Misc::TutorialSetFlag& packet);
//Pet
void HandlePetAction(WorldPacket& recvData);
void HandlePetAction(WorldPackets::Pet::PetAction& packet);
void HandlePetStopAttack(WorldPackets::Pet::PetStopAttack& packet);
void HandlePetActionHelper(Unit* pet, ObjectGuid guid1, uint32 spellid, uint16 flag, ObjectGuid guid2, float x, float y, float z);
void HandleQueryPetName(WorldPackets::Query::QueryPetName& packet);
void HandlePetSetAction(WorldPacket& recvData);
void HandlePetSetAction(WorldPackets::Pet::PetSetAction& packet);
void HandlePetAbandon(WorldPackets::Pet::PetAbandon& packet);
void HandlePetRename(WorldPacket& recvData);
void HandlePetRename(WorldPackets::Pet::PetRename& packet);
void HandlePetCancelAuraOpcode(WorldPackets::Spells::PetCancelAura& packet);
void HandlePetSpellAutocastOpcode(WorldPackets::Pet::PetSpellAutocast& packet);
void HandlePetCastSpellOpcode(WorldPackets::Spells::PetCastSpell& petCastSpell);
+4 -5
View File
@@ -17,6 +17,7 @@
#include "SpellHistory.h"
#include "Pet.h"
#include "PetPackets.h"
#include "Player.h"
#include "SpellInfo.h"
#include "SpellPackets.h"
@@ -335,16 +336,14 @@ void SpellHistory::WritePacket(WorldPackets::Spells::SendSpellCharges* sendSpell
}
}
/*
template<>
void SpellHistory::WritePacket(WorldPackets::Pet::PetSpells* petSpells)
void SpellHistory::WritePacket(WorldPackets::Pet::PetSpells* petSpells) const
{
Clock::time_point now = Clock::now();
petSpells->Cooldowns.reserve(_spellCooldowns.size());
for (auto const& p : _spellCooldowns)
{
SpellInfo const* spellInfo = sSpellMgr->AssertSpellInfo(p.first);
WorldPackets::Pet::PetSpellCooldown petSpellCooldown;
petSpellCooldown.SpellID = p.first;
petSpellCooldown.Category = p.second.CategoryId;
@@ -361,7 +360,7 @@ void SpellHistory::WritePacket(WorldPackets::Pet::PetSpells* petSpells)
petSpellCooldown.CategoryDuration = uint32(categoryDuration.count());
}
petSpells->Cooldowns.push_back(historyEntry);
petSpells->Cooldowns.push_back(petSpellCooldown);
}
petSpells->SpellHistory.reserve(_categoryCharges.size());
@@ -382,7 +381,7 @@ void SpellHistory::WritePacket(WorldPackets::Pet::PetSpells* petSpells)
}
}
}
*/
void SpellHistory::StartCooldown(SpellInfo const* spellInfo, uint32 itemId, Spell* spell /*= nullptr*/, bool onHold /*= false*/)
{