diff --git a/common/features.h b/common/features.h index 486255f28..a35431bff 100644 --- a/common/features.h +++ b/common/features.h @@ -219,6 +219,9 @@ enum { //some random constants //the square of the maximum range at whihc you could possibly use NPC services (shop, tribute, etc) #define USE_NPC_RANGE2 200*200 //arbitrary right now +// Squared range for rampage 75.0 * 75.0 for now +#define NPC_RAMPAGE_RANGE2 5625.0f + //the formula for experience for killing a mob. //level is the only valid variable to use #define EXP_FORMULA level*level*75*35/10 diff --git a/zone/mob_ai.cpp b/zone/mob_ai.cpp index ed55d1146..b82f8601a 100644 --- a/zone/mob_ai.cpp +++ b/zone/mob_ai.cpp @@ -2074,15 +2074,34 @@ bool Mob::Rampage(ExtraAttackOptions *opts) if (m_target) { if (m_target == GetTarget()) continue; - if (CombatRange(m_target)) { + if (DistanceSquaredNoZ(GetPosition(), m_target->GetPosition()) <= NPC_RAMPAGE_RANGE2) { ProcessAttackRounds(m_target, opts); index_hit++; } } } - if (RuleB(Combat, RampageHitsTarget) && index_hit < rampage_targets) - ProcessAttackRounds(GetTarget(), opts); + if (RuleB(Combat, RampageHitsTarget)) { + if (index_hit < rampage_targets) + ProcessAttackRounds(GetTarget(), opts); + } else { // let's do correct behavior here, if they set above rule we can assume they want non-live like behavior + if (index_hit < rampage_targets) { + // so we go over in reverse order and skip range check + // lets do it this way to still support non-live-like >1 rampage targets + // likely live is just a fall through of the last valid mob + for (auto i = RampageArray.crbegin(); i != RampageArray.crend(); ++i) { + if (index_hit >= rampage_targets) + break; + auto m_target = entity_list.GetMob(*i); + if (m_target) { + if (m_target == GetTarget()) + continue; + ProcessAttackRounds(m_target, opts); + index_hit++; + } + } + } + } m_specialattacks = eSpecialAttacks::None;