diff --git a/src/game/SharedDefines.h b/src/game/SharedDefines.h index 2a047d913..07a245494 100644 --- a/src/game/SharedDefines.h +++ b/src/game/SharedDefines.h @@ -1055,7 +1055,7 @@ enum Targets TARGET_GAMEOBJECT_ITEM = 26, TARGET_MASTER = 27, TARGET_ALL_ENEMY_IN_AREA_CHANNELED = 28, - TARGET_ALL_FRIENDLY_UNITS_AROUND_CASTER = 30, // in TargetB used only with TARGET_ALL_AROUND_CASTER and in self casting range in TargetA + TARGET_ALL_FRIENDLY_UNITS_AROUND_CASTER = 30, // select friendly for caster object faction (in different original caster faction) in TargetB used only with TARGET_ALL_AROUND_CASTER and in self casting range in TargetA TARGET_ALL_FRIENDLY_UNITS_IN_AREA = 31, TARGET_MINION = 32, TARGET_ALL_PARTY = 33, diff --git a/src/game/Spell.cpp b/src/game/Spell.cpp index 0b76eb390..8920349f4 100644 --- a/src/game/Spell.cpp +++ b/src/game/Spell.cpp @@ -1862,7 +1862,8 @@ void Spell::SetTargetMap(SpellEffectIndex effIndex, uint32 targetMode, UnitList& FillRaidOrPartyManaPriorityTargets(targetUnitMap, m_caster, m_caster, radius, 3, true, false, false); break; default: - FillAreaTargets(targetUnitMap, m_targets.m_destX, m_targets.m_destY, radius, PUSH_SELF_CENTER, SPELL_TARGETS_FRIENDLY); + // selected friendly units (for casting objects) around casting object + FillAreaTargets(targetUnitMap, m_targets.m_destX, m_targets.m_destY, radius, PUSH_SELF_CENTER, SPELL_TARGETS_FRIENDLY, GetCastingObject()); break; } break; @@ -6401,13 +6402,24 @@ SpellCastResult Spell::CanOpenLock(SpellEffectIndex effIndex, uint32 lockId, Ski return SPELL_CAST_OK; } -void Spell::FillAreaTargets(UnitList &targetUnitMap, float x, float y, float radius, SpellNotifyPushType pushType, SpellTargets spellTargets) +/* + * Fill target list by units around (x,y) points at radius distance + + * @param targetUnitMap Reference to target list that filled by function + * @param x X coordinates of center point for target search + * @param y Y coordinates of center point for target search + * @param radius Radius around (x,y) for target search + * @param pushType Additional rules for target area selection (in front, angle, etc) + * @param spellTargets Additional rules for target selection base at hostile/friendly state to original spell caster + * @param originalCaster If provided set alternative original caster, if =NULL then used Spell::GetAffectiveObject() return + */ +void Spell::FillAreaTargets(UnitList &targetUnitMap, float x, float y, float radius, SpellNotifyPushType pushType, SpellTargets spellTargets, WorldObject* originalCaster /*=NULL*/) { CellPair p(MaNGOS::ComputeCellPair(x, y)); Cell cell(p); cell.data.Part.reserved = ALL_DISTRICT; cell.SetNoCreate(); - MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, targetUnitMap, radius, pushType, spellTargets); + MaNGOS::SpellNotifierCreatureAndPlayer notifier(*this, targetUnitMap, radius, pushType, spellTargets, originalCaster); TypeContainerVisitor world_notifier(notifier); TypeContainerVisitor grid_notifier(notifier); cell.Visit(p, world_notifier, *m_caster->GetMap(), *m_caster, radius); diff --git a/src/game/Spell.h b/src/game/Spell.h index 7cda2c8d1..69c2dbcaf 100644 --- a/src/game/Spell.h +++ b/src/game/Spell.h @@ -411,7 +411,7 @@ class Spell void FillTargetMap(); void SetTargetMap(SpellEffectIndex effIndex, uint32 targetMode, UnitList &targetUnitMap); - void FillAreaTargets(UnitList &targetUnitMap, float x, float y, float radius, SpellNotifyPushType pushType, SpellTargets spellTargets); + void FillAreaTargets(UnitList &targetUnitMap, float x, float y, float radius, SpellNotifyPushType pushType, SpellTargets spellTargets, WorldObject* originalCaster = NULL); void FillRaidOrPartyTargets(UnitList &targetUnitMap, Unit* member, Unit* center, float radius, bool raid, bool withPets, bool withcaster); void FillRaidOrPartyManaPriorityTargets(UnitList &targetUnitMap, Unit* member, Unit* center, float radius, uint32 count, bool raid, bool withPets, bool withcaster); void FillRaidOrPartyHealthPriorityTargets(UnitList &targetUnitMap, Unit* member, Unit* center, float radius, uint32 count, bool raid, bool withPets, bool withcaster); @@ -695,10 +695,12 @@ namespace MaNGOS bool i_playerControled; SpellNotifierCreatureAndPlayer(Spell &spell, std::list &data, float radius, SpellNotifyPushType type, - SpellTargets TargetType = SPELL_TARGETS_NOT_FRIENDLY) - : i_data(&data), i_spell(spell), i_push_type(type), i_radius(radius), i_TargetType(TargetType) + SpellTargets TargetType = SPELL_TARGETS_NOT_FRIENDLY, WorldObject* originalCaster = NULL) + : i_data(&data), i_spell(spell), i_push_type(type), i_radius(radius), i_TargetType(TargetType), + i_originalCaster(originalCaster) { - i_originalCaster = i_spell.GetAffectiveCasterObject(); + if (!i_originalCaster) + i_originalCaster = i_spell.GetAffectiveCasterObject(); i_playerControled = i_originalCaster ? i_originalCaster->IsControlledByPlayer() : false; } diff --git a/src/game/SpellMgr.cpp b/src/game/SpellMgr.cpp index d8aa6bebf..fe14e20c4 100644 --- a/src/game/SpellMgr.cpp +++ b/src/game/SpellMgr.cpp @@ -411,9 +411,9 @@ bool IsSingleFromSpellSpecificPerTarget(SpellSpecific spellSpec1,SpellSpecific s bool IsPositiveTarget(uint32 targetA, uint32 targetB) { - // non-positive targets switch(targetA) { + // non-positive targets case TARGET_CHAIN_DAMAGE: case TARGET_ALL_ENEMY_IN_AREA: case TARGET_ALL_ENEMY_IN_AREA_INSTANT: @@ -423,6 +423,7 @@ bool IsPositiveTarget(uint32 targetA, uint32 targetB) case TARGET_SINGLE_ENEMY: case TARGET_IN_FRONT_OF_CASTER_30: return false; + // positive or dependent case TARGET_CASTER_COORDINATES: return (targetB == TARGET_ALL_PARTY || targetB == TARGET_ALL_FRIENDLY_UNITS_AROUND_CASTER); default: diff --git a/src/shared/revision_nr.h b/src/shared/revision_nr.h index d43087157..32d17a400 100644 --- a/src/shared/revision_nr.h +++ b/src/shared/revision_nr.h @@ -1,4 +1,4 @@ #ifndef __REVISION_NR_H__ #define __REVISION_NR_H__ - #define REVISION_NR "9875" + #define REVISION_NR "9876" #endif // __REVISION_NR_H__