mirror of
https://github.com/mangosfour/server.git
synced 2025-12-13 22:37:03 +00:00
[7089] Implement ITEM_ENCHANTMENT_TYPE_USE_SPELL support.
This allow cast spells at item used from engineering recipes 54999, 54736, 54998, 55002, 55016, 54793.
This commit is contained in:
parent
c0824b35c6
commit
633cad5a56
8 changed files with 105 additions and 64 deletions
|
|
@ -152,7 +152,7 @@ enum EnchantmentSlot
|
||||||
SOCK_ENCHANTMENT_SLOT_2 = 3,
|
SOCK_ENCHANTMENT_SLOT_2 = 3,
|
||||||
SOCK_ENCHANTMENT_SLOT_3 = 4,
|
SOCK_ENCHANTMENT_SLOT_3 = 4,
|
||||||
BONUS_ENCHANTMENT_SLOT = 5,
|
BONUS_ENCHANTMENT_SLOT = 5,
|
||||||
WOTLK_ENCHANTMENT_SLOT = 6,
|
PRISMATIC_ENCHANTMENT_SLOT = 6, // added at apply special permanent enchantment
|
||||||
MAX_INSPECTED_ENCHANTMENT_SLOT = 7,
|
MAX_INSPECTED_ENCHANTMENT_SLOT = 7,
|
||||||
|
|
||||||
PROP_ENCHANTMENT_SLOT_0 = 7, // used with RandomSuffix
|
PROP_ENCHANTMENT_SLOT_0 = 7, // used with RandomSuffix
|
||||||
|
|
|
||||||
|
|
@ -6947,6 +6947,92 @@ void Player::CastItemCombatSpell(Item *item,Unit* Target, WeaponAttackType attTy
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Player::CastItemUseSpell(Item *item,SpellCastTargets const& targets,uint8 cast_count, uint32 glyphIndex)
|
||||||
|
{
|
||||||
|
ItemPrototype const* proto = item->GetProto();
|
||||||
|
// special learning case
|
||||||
|
if(proto->Spells[0].SpellId==SPELL_ID_GENERIC_LEARN || proto->Spells[0].SpellId==SPELL_ID_GENERIC_LEARN_PET)
|
||||||
|
{
|
||||||
|
uint32 learn_spell_id = proto->Spells[0].SpellId;
|
||||||
|
uint32 learning_spell_id = proto->Spells[1].SpellId;
|
||||||
|
|
||||||
|
SpellEntry const *spellInfo = sSpellStore.LookupEntry(learn_spell_id);
|
||||||
|
if(!spellInfo)
|
||||||
|
{
|
||||||
|
sLog.outError("Player::CastItemUseSpell: Item (Entry: %u) in have wrong spell id %u, ignoring ",proto->ItemId, learn_spell_id);
|
||||||
|
SendEquipError(EQUIP_ERR_NONE,item,NULL);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Spell *spell = new Spell(this, spellInfo, false);
|
||||||
|
spell->m_CastItem = item;
|
||||||
|
spell->m_cast_count = cast_count; //set count of casts
|
||||||
|
spell->m_currentBasePoints[0] = learning_spell_id;
|
||||||
|
spell->prepare(&targets);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// use triggered flag only for items with many spell casts and for not first cast
|
||||||
|
int count = 0;
|
||||||
|
|
||||||
|
// item spells casted at use
|
||||||
|
for(int i = 0; i < 5; ++i)
|
||||||
|
{
|
||||||
|
_Spell const& spellData = proto->Spells[i];
|
||||||
|
|
||||||
|
// no spell
|
||||||
|
if(!spellData.SpellId)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
// wrong triggering type
|
||||||
|
if( spellData.SpellTrigger != ITEM_SPELLTRIGGER_ON_USE && spellData.SpellTrigger != ITEM_SPELLTRIGGER_ON_NO_DELAY_USE)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
SpellEntry const *spellInfo = sSpellStore.LookupEntry(spellData.SpellId);
|
||||||
|
if(!spellInfo)
|
||||||
|
{
|
||||||
|
sLog.outError("Player::CastItemUseSpell: Item (Entry: %u) in have wrong spell id %u, ignoring",proto->ItemId, spellData.SpellId);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
Spell *spell = new Spell(this, spellInfo, (count > 0));
|
||||||
|
spell->m_CastItem = item;
|
||||||
|
spell->m_cast_count = cast_count; // set count of casts
|
||||||
|
spell->m_glyphIndex = glyphIndex; // glyph index
|
||||||
|
spell->prepare(&targets);
|
||||||
|
|
||||||
|
++count;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Item enchantments spells casted at use
|
||||||
|
for(int e_slot = 0; e_slot < MAX_ENCHANTMENT_SLOT; ++e_slot)
|
||||||
|
{
|
||||||
|
uint32 enchant_id = item->GetEnchantmentId(EnchantmentSlot(e_slot));
|
||||||
|
SpellItemEnchantmentEntry const *pEnchant = sSpellItemEnchantmentStore.LookupEntry(enchant_id);
|
||||||
|
if(!pEnchant) continue;
|
||||||
|
for (int s=0;s<3;s++)
|
||||||
|
{
|
||||||
|
if(pEnchant->type[s]!=ITEM_ENCHANTMENT_TYPE_USE_SPELL)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
SpellEntry const *spellInfo = sSpellStore.LookupEntry(pEnchant->spellid[s]);
|
||||||
|
if (!spellInfo)
|
||||||
|
{
|
||||||
|
sLog.outError("Player::CastItemUseSpell Enchant %i, cast unknown spell %i", pEnchant->ID, pEnchant->spellid[s]);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
Spell *spell = new Spell(this, spellInfo, (count > 0));
|
||||||
|
spell->m_CastItem = item;
|
||||||
|
spell->m_cast_count = cast_count; // set count of casts
|
||||||
|
spell->m_glyphIndex = glyphIndex; // glyph index
|
||||||
|
spell->prepare(&targets);
|
||||||
|
|
||||||
|
++count;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void Player::_RemoveAllItemMods()
|
void Player::_RemoveAllItemMods()
|
||||||
{
|
{
|
||||||
sLog.outDebug("_RemoveAllItemMods start.");
|
sLog.outDebug("_RemoveAllItemMods start.");
|
||||||
|
|
@ -11876,6 +11962,9 @@ void Player::ApplyEnchantment(Item *item,EnchantmentSlot slot,bool apply, bool a
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case ITEM_ENCHANTMENT_TYPE_USE_SPELL:
|
||||||
|
// processed in Player::CastItemUseSpell
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
sLog.outError("Unknown item enchantment display type: %d",enchant_display_type);
|
sLog.outError("Unknown item enchantment display type: %d",enchant_display_type);
|
||||||
break;
|
break;
|
||||||
|
|
|
||||||
|
|
@ -46,6 +46,7 @@ class Pet;
|
||||||
class PlayerMenu;
|
class PlayerMenu;
|
||||||
class Transport;
|
class Transport;
|
||||||
class UpdateMask;
|
class UpdateMask;
|
||||||
|
class SpellCastTargets;
|
||||||
class PlayerSocial;
|
class PlayerSocial;
|
||||||
class AchievementMgr;
|
class AchievementMgr;
|
||||||
class Vehicle;
|
class Vehicle;
|
||||||
|
|
@ -1871,6 +1872,7 @@ class MANGOS_DLL_SPEC Player : public Unit
|
||||||
void ApplyEquipSpell(SpellEntry const* spellInfo, Item* item, bool apply, bool form_change = false);
|
void ApplyEquipSpell(SpellEntry const* spellInfo, Item* item, bool apply, bool form_change = false);
|
||||||
void UpdateEquipSpellsAtFormChange();
|
void UpdateEquipSpellsAtFormChange();
|
||||||
void CastItemCombatSpell(Item *item,Unit* Target, WeaponAttackType attType);
|
void CastItemCombatSpell(Item *item,Unit* Target, WeaponAttackType attType);
|
||||||
|
void CastItemUseSpell(Item *item,SpellCastTargets const& targets,uint8 cast_count, uint32 glyphIndex);
|
||||||
|
|
||||||
void SendInitWorldStates();
|
void SendInitWorldStates();
|
||||||
void SendUpdateWorldState(uint32 Field, uint32 Value);
|
void SendUpdateWorldState(uint32 Field, uint32 Value);
|
||||||
|
|
|
||||||
|
|
@ -2036,7 +2036,7 @@ void Spell::SetTargetMap(uint32 i,uint32 cur,std::list<Unit*> &TagUnitMap)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Spell::prepare(SpellCastTargets * targets, Aura* triggeredByAura)
|
void Spell::prepare(SpellCastTargets const* targets, Aura* triggeredByAura)
|
||||||
{
|
{
|
||||||
m_targets = *targets;
|
m_targets = *targets;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -321,7 +321,7 @@ class Spell
|
||||||
Spell( Unit* Caster, SpellEntry const *info, bool triggered, uint64 originalCasterGUID = 0, Spell** triggeringContainer = NULL );
|
Spell( Unit* Caster, SpellEntry const *info, bool triggered, uint64 originalCasterGUID = 0, Spell** triggeringContainer = NULL );
|
||||||
~Spell();
|
~Spell();
|
||||||
|
|
||||||
void prepare(SpellCastTargets * targets, Aura* triggeredByAura = NULL);
|
void prepare(SpellCastTargets const* targets, Aura* triggeredByAura = NULL);
|
||||||
void cancel();
|
void cancel();
|
||||||
void update(uint32 difftime);
|
void update(uint32 difftime);
|
||||||
void cast(bool skipCheck = false);
|
void cast(bool skipCheck = false);
|
||||||
|
|
|
||||||
|
|
@ -125,59 +125,7 @@ void WorldSession::HandleUseItemOpcode(WorldPacket& recvPacket)
|
||||||
if(!Script->ItemUse(pUser,pItem,targets))
|
if(!Script->ItemUse(pUser,pItem,targets))
|
||||||
{
|
{
|
||||||
// no script or script not process request by self
|
// no script or script not process request by self
|
||||||
|
pUser->CastItemUseSpell(pItem,targets,cast_count,glyphIndex);
|
||||||
// special learning case
|
|
||||||
if((pItem->GetProto()->Spells[0].SpellId==SPELL_ID_GENERIC_LEARN) || (pItem->GetProto()->Spells[0].SpellId==SPELL_ID_GENERIC_LEARN_PET))
|
|
||||||
{
|
|
||||||
uint32 learn_spell_id = pItem->GetProto()->Spells[0].SpellId;
|
|
||||||
uint32 learning_spell_id = pItem->GetProto()->Spells[1].SpellId;
|
|
||||||
|
|
||||||
SpellEntry const *spellInfo = sSpellStore.LookupEntry(learn_spell_id);
|
|
||||||
if(!spellInfo)
|
|
||||||
{
|
|
||||||
sLog.outError("Item (Entry: %u) in have wrong spell id %u, ignoring ",proto->ItemId, learn_spell_id);
|
|
||||||
pUser->SendEquipError(EQUIP_ERR_NONE,pItem,NULL);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
Spell *spell = new Spell(pUser, spellInfo, false);
|
|
||||||
spell->m_CastItem = pItem;
|
|
||||||
spell->m_cast_count = cast_count; //set count of casts
|
|
||||||
spell->m_currentBasePoints[0] = learning_spell_id;
|
|
||||||
spell->prepare(&targets);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// use triggered flag only for items with many spell casts and for not first cast
|
|
||||||
int count = 0;
|
|
||||||
|
|
||||||
for(int i = 0; i < 5; ++i)
|
|
||||||
{
|
|
||||||
_Spell const& spellData = pItem->GetProto()->Spells[i];
|
|
||||||
|
|
||||||
// no spell
|
|
||||||
if(!spellData.SpellId)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
// wrong triggering type
|
|
||||||
if( spellData.SpellTrigger != ITEM_SPELLTRIGGER_ON_USE && spellData.SpellTrigger != ITEM_SPELLTRIGGER_ON_NO_DELAY_USE)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
SpellEntry const *spellInfo = sSpellStore.LookupEntry(spellData.SpellId);
|
|
||||||
if(!spellInfo)
|
|
||||||
{
|
|
||||||
sLog.outError("Item (Entry: %u) in have wrong spell id %u, ignoring ",proto->ItemId, spellData.SpellId);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
Spell *spell = new Spell(pUser, spellInfo, (count > 0));
|
|
||||||
spell->m_CastItem = pItem;
|
|
||||||
spell->m_cast_count = cast_count; // set count of casts
|
|
||||||
spell->m_glyphIndex = glyphIndex; // glyph index
|
|
||||||
spell->prepare(&targets);
|
|
||||||
|
|
||||||
++count;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -251,13 +251,15 @@ enum AbilytyLearnType
|
||||||
|
|
||||||
enum ItemEnchantmentType
|
enum ItemEnchantmentType
|
||||||
{
|
{
|
||||||
ITEM_ENCHANTMENT_TYPE_NONE = 0,
|
ITEM_ENCHANTMENT_TYPE_NONE = 0,
|
||||||
ITEM_ENCHANTMENT_TYPE_COMBAT_SPELL = 1,
|
ITEM_ENCHANTMENT_TYPE_COMBAT_SPELL = 1,
|
||||||
ITEM_ENCHANTMENT_TYPE_DAMAGE = 2,
|
ITEM_ENCHANTMENT_TYPE_DAMAGE = 2,
|
||||||
ITEM_ENCHANTMENT_TYPE_EQUIP_SPELL = 3,
|
ITEM_ENCHANTMENT_TYPE_EQUIP_SPELL = 3,
|
||||||
ITEM_ENCHANTMENT_TYPE_RESISTANCE = 4,
|
ITEM_ENCHANTMENT_TYPE_RESISTANCE = 4,
|
||||||
ITEM_ENCHANTMENT_TYPE_STAT = 5,
|
ITEM_ENCHANTMENT_TYPE_STAT = 5,
|
||||||
ITEM_ENCHANTMENT_TYPE_TOTEM = 6
|
ITEM_ENCHANTMENT_TYPE_TOTEM = 6,
|
||||||
|
ITEM_ENCHANTMENT_TYPE_USE_SPELL = 7,
|
||||||
|
ITEM_ENCHANTMENT_TYPE_PRISMATIC_SOCKET = 8
|
||||||
};
|
};
|
||||||
|
|
||||||
enum TotemCategoryType
|
enum TotemCategoryType
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
||||||
#ifndef __REVISION_NR_H__
|
#ifndef __REVISION_NR_H__
|
||||||
#define __REVISION_NR_H__
|
#define __REVISION_NR_H__
|
||||||
#define REVISION_NR "7088"
|
#define REVISION_NR "7089"
|
||||||
#endif // __REVISION_NR_H__
|
#endif // __REVISION_NR_H__
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue