From 352d6fd83c436b467d2cf555fbe8173fed6922ee Mon Sep 17 00:00:00 2001 From: KayenEQ Date: Thu, 13 Nov 2014 05:19:01 -0500 Subject: [PATCH] Support for all remaining known spell target types. Implemented target type (32) AE Target HateList Implemented target type (36) Area Client Only Implemented target type (37) Area PC Only Implemented target type (39) Group No Pet --- changelog.txt | 4 +++ common/spdat.h | 2 +- zone/effects.cpp | 4 +++ zone/groups.cpp | 4 +-- zone/hate_list.cpp | 11 +++++--- zone/hate_list.h | 2 +- zone/raids.cpp | 4 +-- zone/spells.cpp | 62 ++++++++++++++++++++++++++++++++++++++++++---- 8 files changed, 78 insertions(+), 15 deletions(-) diff --git a/changelog.txt b/changelog.txt index b80128505..d72b4ca23 100644 --- a/changelog.txt +++ b/changelog.txt @@ -2,6 +2,10 @@ EQEMu Changelog (Started on Sept 24, 2003 15:50) ------------------------------------------------------- == 11/13/2014 == Kayen: Implemented target type (44) 'Beams' (which projects an AE infront of caster with a specified length and width). +Kayen: Implemented target type (32) AE Target HateList +Kayen: Implemented target type (36) Area Client Only +Kayen: Implemented target type (37) Area PC Only +Kayen: Implemented target type (39) Group No Pet == 11/12/2014 == Uleat: Changed 'GMTrainee' struct to reflect the actual client hard-coded max skill count (100) - applies to all currently supported clients (6.2->RoF) diff --git a/common/spdat.h b/common/spdat.h index b71b3c2ad..da2e4486c 100644 --- a/common/spdat.h +++ b/common/spdat.h @@ -119,7 +119,7 @@ typedef enum { /* 29 */ // NOT USED /* 30 */ // NOT USED /* 31 */ // NOT USED -/* 32 */ ST_AECaster2 = 0x20, //ae caster hatelist maybe? +/* 32 */ ST_AETargetHateList = 0x20, /* 33 */ ST_HateList = 0x21, /* 34 */ ST_LDoNChest_Cursed = 0x22, /* 35 */ ST_Muramite = 0x23, //only works on special muramites diff --git a/zone/effects.cpp b/zone/effects.cpp index 9888258d9..16024c169 100644 --- a/zone/effects.cpp +++ b/zone/effects.cpp @@ -766,6 +766,10 @@ void EntityList::AESpell(Mob *caster, Mob *center, uint16 spell_id, bool affect_ continue; if (spells[spell_id].targettype == ST_TargetAENoPlayersPets && curmob->IsPetOwnerClient()) continue; + if (spells[spell_id].targettype == ST_AreaClientOnly && !curmob->IsClient()) + continue; + if (spells[spell_id].targettype == ST_AreaNPCOnly && !curmob->IsNPC()) + continue; if (spells[spell_id].targettype == ST_Ring) { dist_targ = curmob->DistNoRoot(caster->GetTargetRingX(), caster->GetTargetRingY(), caster->GetTargetRingZ()); diff --git a/zone/groups.cpp b/zone/groups.cpp index e80650f08..ae51f51c9 100644 --- a/zone/groups.cpp +++ b/zone/groups.cpp @@ -693,7 +693,7 @@ void Group::CastGroupSpell(Mob* caster, uint16 spell_id) { if(members[z] == caster) { caster->SpellOnTarget(spell_id, caster); #ifdef GROUP_BUFF_PETS - if(caster->GetPet() && caster->HasPetAffinity() && !caster->GetPet()->IsCharmed()) + if(spells[spell_id].targettype != ST_GroupNoPets && caster->GetPet() && caster->HasPetAffinity() && !caster->GetPet()->IsCharmed()) caster->SpellOnTarget(spell_id, caster->GetPet()); #endif } @@ -704,7 +704,7 @@ void Group::CastGroupSpell(Mob* caster, uint16 spell_id) { members[z]->CalcSpellPowerDistanceMod(spell_id, distance); caster->SpellOnTarget(spell_id, members[z]); #ifdef GROUP_BUFF_PETS - if(members[z]->GetPet() && members[z]->HasPetAffinity() && !members[z]->GetPet()->IsCharmed()) + if(spells[spell_id].targettype != ST_GroupNoPets && members[z]->GetPet() && members[z]->HasPetAffinity() && !members[z]->GetPet()->IsCharmed()) caster->SpellOnTarget(spell_id, members[z]->GetPet()); #endif } else diff --git a/zone/hate_list.cpp b/zone/hate_list.cpp index e9117db98..2ee904453 100644 --- a/zone/hate_list.cpp +++ b/zone/hate_list.cpp @@ -557,12 +557,15 @@ int HateList::AreaRampage(Mob *caster, Mob *target, int count, ExtraAttackOption return ret; } -void HateList::SpellCast(Mob *caster, uint32 spell_id, float range) +void HateList::SpellCast(Mob *caster, uint32 spell_id, float range, Mob* ae_center) { if(!caster) - { return; - } + + Mob* center = caster; + + if (ae_center) + center = ae_center; //this is slower than just iterating through the list but avoids //crashes when people kick the bucket in the middle of this call @@ -578,7 +581,7 @@ void HateList::SpellCast(Mob *caster, uint32 spell_id, float range) tHateEntry *h = (*iterator); if(range > 0) { - dist_targ = caster->DistNoRoot(*h->ent); + dist_targ = center->DistNoRoot(*h->ent); if(dist_targ <= range && dist_targ >= min_range2) { id_list.push_back(h->ent->GetID()); diff --git a/zone/hate_list.h b/zone/hate_list.h index a3e6c6a88..4ea8d0bd6 100644 --- a/zone/hate_list.h +++ b/zone/hate_list.h @@ -63,7 +63,7 @@ public: int AreaRampage(Mob *caster, Mob *target, int count, ExtraAttackOptions *opts); - void SpellCast(Mob *caster, uint32 spell_id, float range); + void SpellCast(Mob *caster, uint32 spell_id, float range, Mob *ae_center = nullptr); bool IsEmpty(); void PrintToClient(Client *c); diff --git a/zone/raids.cpp b/zone/raids.cpp index 041b92ad4..d1e8db464 100644 --- a/zone/raids.cpp +++ b/zone/raids.cpp @@ -478,7 +478,7 @@ void Raid::CastGroupSpell(Mob* caster, uint16 spellid, uint32 gid) if(members[x].member == caster) { caster->SpellOnTarget(spellid, caster); #ifdef GROUP_BUFF_PETS - if(caster->GetPet() && caster->HasPetAffinity() && !caster->GetPet()->IsCharmed()) + if(spells[spellid].targettype != ST_GroupNoPets && caster->GetPet() && caster->HasPetAffinity() && !caster->GetPet()->IsCharmed()) caster->SpellOnTarget(spellid, caster->GetPet()); #endif } @@ -489,7 +489,7 @@ void Raid::CastGroupSpell(Mob* caster, uint16 spellid, uint32 gid) if(distance <= range2){ caster->SpellOnTarget(spellid, members[x].member); #ifdef GROUP_BUFF_PETS - if(members[x].member->GetPet() && members[x].member->HasPetAffinity() && !members[x].member->GetPet()->IsCharmed()) + if(spells[spellid].targettype != ST_GroupNoPets && members[x].member->GetPet() && members[x].member->HasPetAffinity() && !members[x].member->GetPet()->IsCharmed()) caster->SpellOnTarget(spellid, members[x].member->GetPet()); #endif } diff --git a/zone/spells.cpp b/zone/spells.cpp index e6cab8422..5b8bfef39 100644 --- a/zone/spells.cpp +++ b/zone/spells.cpp @@ -1611,7 +1611,45 @@ bool Mob::DetermineSpellTargets(uint16 spell_id, Mob *&spell_target, Mob *&ae_ce break; } + case ST_AETargetHateList: + { + if (spells[spell_id].range > 0) + { + if(!spell_target) + return false; + + ae_center = spell_target; + CastAction = AETarget; + } + else { + spell_target = nullptr; + ae_center = this; + CastAction = CAHateList; + } + break; + } + + case ST_AreaClientOnly: + case ST_AreaNPCOnly: + { + if (spells[spell_id].range > 0) + { + if(!spell_target) + return false; + + ae_center = spell_target; + CastAction = AETarget; + } + else { + spell_target = nullptr; + ae_center = this; + CastAction = AECaster; + } + break; + } + case ST_UndeadAE: //should only affect undead... + case ST_SummonedAE: case ST_TargetAETap: case ST_AETarget: case ST_TargetAENoPlayersPets: @@ -1630,6 +1668,7 @@ bool Mob::DetermineSpellTargets(uint16 spell_id, Mob *&spell_target, Mob *&ae_ce // Group spells case ST_GroupTeleport: case ST_Group: + case ST_GroupNoPets: { if(IsClient() && CastToClient()->TGB() && IsTGBCompatibleSpell(spell_id)) { if( (!target) || @@ -2043,15 +2082,28 @@ bool Mob::SpellFinished(uint16 spell_id, Mob *spell_target, uint16 slot, uint16 } else { // regular PB AE or targeted AE spell - spell_target is null if PB if(spell_target) // this must be an AETarget spell - { + { + bool cast_on_target = true; + if (spells[spell_id].targettype == ST_TargetAENoPlayersPets && spell_target->IsPetOwnerClient()) + cast_on_target = false; + if (spells[spell_id].targettype == ST_AreaClientOnly && !spell_target->IsClient()) + cast_on_target = false; + if (spells[spell_id].targettype == ST_AreaNPCOnly && !spell_target->IsNPC()) + cast_on_target = false; + // affect the target too - SpellOnTarget(spell_id, spell_target, false, true, resist_adjust); + if (cast_on_target) + SpellOnTarget(spell_id, spell_target, false, true, resist_adjust); } if(ae_center && ae_center == this && IsBeneficialSpell(spell_id)) SpellOnTarget(spell_id, this); bool affect_caster = !IsNPC(); //NPC AE spells do not affect the NPC caster - entity_list.AESpell(this, ae_center, spell_id, affect_caster, resist_adjust); + + if (spells[spell_id].targettype == ST_AETargetHateList) + hate_list.SpellCast(this, spell_id, spells[spell_id].aoerange, ae_center); + else + entity_list.AESpell(this, ae_center, spell_id, affect_caster, resist_adjust); } break; } @@ -2109,7 +2161,7 @@ bool Mob::SpellFinished(uint16 spell_id, Mob *spell_target, uint16 slot, uint16 SpellOnTarget(spell_id, this); #ifdef GROUP_BUFF_PETS //pet too - if (GetPet() && HasPetAffinity() && !GetPet()->IsCharmed()) + if (spells[spell_id].targettype != ST_GroupNoPets && GetPet() && HasPetAffinity() && !GetPet()->IsCharmed()) SpellOnTarget(spell_id, GetPet()); #endif } @@ -2117,7 +2169,7 @@ bool Mob::SpellFinished(uint16 spell_id, Mob *spell_target, uint16 slot, uint16 SpellOnTarget(spell_id, spell_target); #ifdef GROUP_BUFF_PETS //pet too - if (spell_target->GetPet() && HasPetAffinity() && !spell_target->GetPet()->IsCharmed()) + if (spells[spell_id].targettype != ST_GroupNoPets && spell_target->GetPet() && HasPetAffinity() && !spell_target->GetPet()->IsCharmed()) SpellOnTarget(spell_id, spell_target->GetPet()); #endif }