mirror of
https://github.com/EQEmu/Server.git
synced 2026-03-25 16:52:25 +00:00
Merge pull request #1173 from EQEmu/akkadius/npc-guard-scan-fix
[Bugfix] Very edge case Guard awareness latency
This commit is contained in:
commit
0f5a7e1317
@ -2693,6 +2693,36 @@ void EntityList::RemoveAuraFromMobs(Mob *aura)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The purpose of this system is so that we cache relevant entities that are "close"
|
||||||
|
*
|
||||||
|
* In general; it becomes incredibly expensive to run zone-wide checks against every single mob in the zone when in reality
|
||||||
|
* we only care about entities closest to us
|
||||||
|
*
|
||||||
|
* A very simple example of where this is relevant is Aggro, the below example is skewed because the overall implementation
|
||||||
|
* of Aggro was also tweaked in conjunction with close lists. We also scan more aggressively when entities are moving (1-6 seconds)
|
||||||
|
* versus 60 seconds when idle. We also have entities that are moving add themselves to those closest to them so that their close
|
||||||
|
* lists remain always up to date
|
||||||
|
*
|
||||||
|
* Before: Aggro checks for NPC to Client aggro | (40 clients in zone) x (525 npcs) x 2 (times a second) = 2,520,000 checks a minute
|
||||||
|
* After: Aggro checks for NPC to Client aggro | (40 clients in zone) x (20-30 npcs) x 2 (times a second) = 144,000 checks a minute (This is actually far less today)
|
||||||
|
*
|
||||||
|
* Places in the code where this logic makes a huge impact
|
||||||
|
*
|
||||||
|
* Aggro checks (zone wide -> close)
|
||||||
|
* Aura processing (zone wide -> close)
|
||||||
|
* AE Taunt (zone wide -> close)
|
||||||
|
* AOE Spells (zone wide -> close)
|
||||||
|
* Bard Pulse AOE (zone wide -> close)
|
||||||
|
* Mass Group Buff (zone wide -> close)
|
||||||
|
* AE Attack (zone wide -> close)
|
||||||
|
* Packet QueueCloseClients (zone wide -> close)
|
||||||
|
* Check Close Beneficial Spells (Buffs; should I heal other npcs) (zone wide -> close)
|
||||||
|
* AI Yell for Help (NPC Assist other NPCs) (zone wide -> close)
|
||||||
|
*
|
||||||
|
* All of the above makes a tremendous impact on the bottom line of cpu cycle performance because we run an order of magnitude
|
||||||
|
* less checks by focusing our hot path logic down to a very small subset of relevant entities instead of looping an entire
|
||||||
|
* entity list (zone wide)
|
||||||
|
*
|
||||||
* @param close_mobs
|
* @param close_mobs
|
||||||
* @param scanning_mob
|
* @param scanning_mob
|
||||||
*/
|
*/
|
||||||
@ -5216,6 +5246,8 @@ void EntityList::ReloadMerchants() {
|
|||||||
* If we have a distance requested that is greater than our scanning distance
|
* If we have a distance requested that is greater than our scanning distance
|
||||||
* then we return the full list
|
* then we return the full list
|
||||||
*
|
*
|
||||||
|
* See comments @EntityList::ScanCloseMobs for system explanation
|
||||||
|
*
|
||||||
* @param mob
|
* @param mob
|
||||||
* @param distance
|
* @param distance
|
||||||
* @return
|
* @return
|
||||||
|
|||||||
14
zone/npc.cpp
14
zone/npc.cpp
@ -715,7 +715,7 @@ bool NPC::Process()
|
|||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (IsStunned() && stunned_timer.Check()) {
|
if (IsStunned() && stunned_timer.Check()) {
|
||||||
Mob::UnStun();
|
Mob::UnStun();
|
||||||
this->spun_timer.Disable();
|
this->spun_timer.Disable();
|
||||||
@ -724,7 +724,7 @@ bool NPC::Process()
|
|||||||
SpellProcess();
|
SpellProcess();
|
||||||
|
|
||||||
if (mob_close_scan_timer.Check()) {
|
if (mob_close_scan_timer.Check()) {
|
||||||
entity_list.ScanCloseMobs(close_mobs, this);
|
entity_list.ScanCloseMobs(close_mobs, this, IsMoving());
|
||||||
}
|
}
|
||||||
|
|
||||||
const uint16 npc_mob_close_scan_timer_moving = 6000;
|
const uint16 npc_mob_close_scan_timer_moving = 6000;
|
||||||
@ -1752,7 +1752,7 @@ void NPC::PickPocket(Client* thief)
|
|||||||
steal_item = false;
|
steal_item = false;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto item_inst = database.CreateItem(loot_selection[random].first, loot_selection[random].second);
|
auto item_inst = database.CreateItem(loot_selection[random].first, loot_selection[random].second);
|
||||||
if (item_inst == nullptr) {
|
if (item_inst == nullptr) {
|
||||||
steal_item = false;
|
steal_item = false;
|
||||||
@ -1778,7 +1778,7 @@ void NPC::PickPocket(Client* thief)
|
|||||||
|
|
||||||
while (!steal_item && has_coin) {
|
while (!steal_item && has_coin) {
|
||||||
uint32 coin_amount = zone->random.Int(1, (steal_skill / 25) + 1);
|
uint32 coin_amount = zone->random.Int(1, (steal_skill / 25) + 1);
|
||||||
|
|
||||||
int coin_type = PickPocketPlatinum;
|
int coin_type = PickPocketPlatinum;
|
||||||
while (coin_type <= PickPocketCopper) {
|
while (coin_type <= PickPocketCopper) {
|
||||||
if (money[coin_type]) {
|
if (money[coin_type]) {
|
||||||
@ -2514,10 +2514,10 @@ void NPC::LevelScale() {
|
|||||||
max_hp += (random_level - level) * 100;
|
max_hp += (random_level - level) * 100;
|
||||||
base_hp += (random_level - level) * 100;
|
base_hp += (random_level - level) * 100;
|
||||||
}
|
}
|
||||||
|
|
||||||
current_hp = max_hp;
|
current_hp = max_hp;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Don't add max_dmg to dynamically scaled NPCs since this will be calculated later
|
// Don't add max_dmg to dynamically scaled NPCs since this will be calculated later
|
||||||
if (max_dmg > 0 || skip_auto_scale)
|
if (max_dmg > 0 || skip_auto_scale)
|
||||||
{
|
{
|
||||||
@ -2817,7 +2817,7 @@ FACTION_VALUE NPC::CheckNPCFactionAlly(int32 other_faction) {
|
|||||||
|
|
||||||
// I believe that the assumption is, barring no entry in npc_faction_entries
|
// I believe that the assumption is, barring no entry in npc_faction_entries
|
||||||
// that two npcs on like faction con ally to each other. This catches cases
|
// that two npcs on like faction con ally to each other. This catches cases
|
||||||
// where an npc is on a faction but has no hits (hence no entry in
|
// where an npc is on a faction but has no hits (hence no entry in
|
||||||
// npc_faction_entries).
|
// npc_faction_entries).
|
||||||
|
|
||||||
if (GetPrimaryFaction() == other_faction)
|
if (GetPrimaryFaction() == other_faction)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user