From 0f1c9f10cb37ca7cde14f5d3100692635ff9484a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ji=C5=99=C3=AD=20Sejkora?= Date: Sat, 27 Jul 2024 21:06:27 +0200 Subject: [PATCH] Analytics: Fix rare false negative with invalid despawn events --- .../Results/AgentBuffGainedDeterminer.cs | 24 +++++++++++++++++-- 1 file changed, 22 insertions(+), 2 deletions(-) diff --git a/EVTCAnalytics/Processing/Encounters/Results/AgentBuffGainedDeterminer.cs b/EVTCAnalytics/Processing/Encounters/Results/AgentBuffGainedDeterminer.cs index 3f2c2a04..6ca6130c 100644 --- a/EVTCAnalytics/Processing/Encounters/Results/AgentBuffGainedDeterminer.cs +++ b/EVTCAnalytics/Processing/Encounters/Results/AgentBuffGainedDeterminer.cs @@ -17,7 +17,7 @@ public class AgentBuffGainedDeterminer(Agent agent, uint buffId, bool ignoreInit protected override Event GetEvent(IEnumerable events) { - var filteredEvents = stopAtDespawn ? events.TakeWhile(x => !(x is AgentDespawnEvent despawn && despawn.Agent == agent)) : events; + var filteredEvents = stopAtDespawn ? TakeUntilDespawn(events) : events; if (ignoreInitial) { @@ -29,10 +29,30 @@ protected override Event GetEvent(IEnumerable events) else { return filteredEvents - .TakeWhile(x => x is not AgentDespawnEvent) .OfType() .FirstOrDefault(x => x.Agent == agent && x.Buff.Id == buffId); } } + + private IEnumerable TakeUntilDespawn(IEnumerable events) + { + // Very rarely, arcdps has been seen to emit a despawn event instead of a spawn event + // (specifically, this has been observed once with arcdps 20220330). + // To work around this issue, we ignore despawn events that happen very soon after the first event. + const long earlyDespawnThreshold = 200; + + long firstTime = long.MaxValue; + foreach (var e in events) + { + firstTime = Math.Min(firstTime, e.Time); + + if (e is AgentDespawnEvent despawn && despawn.Agent == agent && despawn.Time - firstTime > earlyDespawnThreshold) + { + yield break; + } + + yield return e; + } + } } }