Fix Rain target limit (massive nerf)

Added rule Spells:OldRainTargets, set to true if you don't want the nerf
This commit is contained in:
Michael Cook (mackal) 2017-06-25 18:18:27 -04:00
parent 497170c453
commit 3e1b75b814
5 changed files with 18 additions and 7 deletions

View File

@ -397,6 +397,7 @@ RULE_BOOL(Spells, FlatItemExtraSpellAmt, false) // allow SpellDmg stat to affect
RULE_BOOL(Spells, IgnoreSpellDmgLvlRestriction, false) // ignore the 5 level spread on applying SpellDmg RULE_BOOL(Spells, IgnoreSpellDmgLvlRestriction, false) // ignore the 5 level spread on applying SpellDmg
RULE_BOOL(Spells, AllowItemTGB, false) // TGB doesn't work with items on live, custom servers want it though RULE_BOOL(Spells, AllowItemTGB, false) // TGB doesn't work with items on live, custom servers want it though
RULE_BOOL(Spells, NPCInnateProcOverride, true) // NPC innate procs override the target type to single target. RULE_BOOL(Spells, NPCInnateProcOverride, true) // NPC innate procs override the target type to single target.
RULE_BOOL(Spells, OldRainTargets, false) // use old incorrectly implemented max targets for rains
RULE_CATEGORY_END() RULE_CATEGORY_END()
RULE_CATEGORY(Combat) RULE_CATEGORY(Combat)

View File

@ -68,6 +68,7 @@ Beacon::Beacon(Mob *at_mob, int lifetime)
resist_adjust = 0; resist_adjust = 0;
spell_iterations = 0; spell_iterations = 0;
caster_id = 0; caster_id = 0;
max_targets = 4; // default
if(lifetime) if(lifetime)
remove_timer.Start(); remove_timer.Start();
@ -93,10 +94,10 @@ bool Beacon::Process()
) )
{ {
Mob *caster = entity_list.GetMob(caster_id); Mob *caster = entity_list.GetMob(caster_id);
if(caster && spell_iterations--) if(caster && spell_iterations-- && max_targets)
{ {
bool affect_caster = (!caster->IsNPC() && !caster->IsAIControlled()); //NPC AE spells do not affect the NPC caster bool affect_caster = (!caster->IsNPC() && !caster->IsAIControlled()); //NPC AE spells do not affect the NPC caster
entity_list.AESpell(caster, this, spell_id, affect_caster, resist_adjust); entity_list.AESpell(caster, this, spell_id, affect_caster, resist_adjust, &max_targets);
} }
else else
{ {
@ -126,6 +127,8 @@ void Beacon::AELocationSpell(Mob *caster, uint16 cast_spell_id, int16 resist_adj
this->resist_adjust = resist_adjust; this->resist_adjust = resist_adjust;
spell_iterations = spells[spell_id].AEDuration / 2500; spell_iterations = spells[spell_id].AEDuration / 2500;
spell_iterations = spell_iterations < 1 ? 1 : spell_iterations; // at least 1 spell_iterations = spell_iterations < 1 ? 1 : spell_iterations; // at least 1
if (spells[spell_id].aemaxtargets)
max_targets = spells[spell_id].aemaxtargets;
spell_timer.Start(2500); spell_timer.Start(2500);
spell_timer.Trigger(); spell_timer.Trigger();
} }

View File

@ -56,6 +56,7 @@ protected:
int16 resist_adjust; int16 resist_adjust;
int spell_iterations; int spell_iterations;
Timer spell_timer; Timer spell_timer;
int max_targets;
uint16 caster_id; uint16 caster_id;
private: private:

View File

@ -694,7 +694,7 @@ void EntityList::AETaunt(Client* taunter, float range, int32 bonus_hate)
// causes caster to hit every mob within dist range of center with // causes caster to hit every mob within dist range of center with
// spell_id. // spell_id.
// NPC spells will only affect other NPCs with compatible faction // NPC spells will only affect other NPCs with compatible faction
void EntityList::AESpell(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster, int16 resist_adjust) void EntityList::AESpell(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster, int16 resist_adjust, int *max_targets)
{ {
Mob *curmob = nullptr; Mob *curmob = nullptr;
@ -709,9 +709,13 @@ void EntityList::AESpell(Mob *caster, Mob *center, uint16 spell_id, bool affect_
bool bad = IsDetrimentalSpell(spell_id); bool bad = IsDetrimentalSpell(spell_id);
bool isnpc = caster->IsNPC(); bool isnpc = caster->IsNPC();
int MAX_TARGETS_ALLOWED = 4;
if (spells[spell_id].aemaxtargets) if (RuleB(Spells, OldRainTargets))
max_targets = nullptr; // ignore it!
int MAX_TARGETS_ALLOWED = max_targets ? *max_targets : 4;
if (!max_targets && spells[spell_id].aemaxtargets)
MAX_TARGETS_ALLOWED = spells[spell_id].aemaxtargets; MAX_TARGETS_ALLOWED = spells[spell_id].aemaxtargets;
int iCounter = 0; int iCounter = 0;
@ -789,8 +793,10 @@ void EntityList::AESpell(Mob *caster, Mob *center, uint16 spell_id, bool affect_
} }
if (!isnpc || spells[spell_id].aemaxtargets) //npcs are not target limited (unless casting a spell with a target limit)... if (!isnpc || spells[spell_id].aemaxtargets) //npcs are not target limited (unless casting a spell with a target limit)...
iCounter++; iCounter++; // should really pull out the MAX_TARGETS_ALLOWED calc so we can break early ...
} }
if (max_targets)
*max_targets = *max_targets - std::min(iCounter, *max_targets); // could be higher than the count
} }
void EntityList::MassGroupBuff(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster) void EntityList::MassGroupBuff(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster)

View File

@ -357,7 +357,7 @@ public:
void AEAttack(Mob *attacker, float dist, int Hand = EQEmu::inventory::slotPrimary, int count = 0, bool IsFromSpell = false); void AEAttack(Mob *attacker, float dist, int Hand = EQEmu::inventory::slotPrimary, int count = 0, bool IsFromSpell = false);
void AETaunt(Client *caster, float range=0, int32 bonus_hate=0); void AETaunt(Client *caster, float range=0, int32 bonus_hate=0);
void AESpell(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster = true, int16 resist_adjust = 0); void AESpell(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster = true, int16 resist_adjust = 0, int *max_targets = nullptr);
void MassGroupBuff(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster = true); void MassGroupBuff(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster = true);
void AEBardPulse(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster = true); void AEBardPulse(Mob *caster, Mob *center, uint16 spell_id, bool affect_caster = true);