protected override void SetCastLogs(ParsedLog log) { CastLog curCastLog = null; long minTime = Math.Max(log.FightData.FightStart, AgentItem.FirstAware); long maxTime = Math.Min(log.FightData.FightEnd, AgentItem.LastAware); foreach (CombatItem c in log.GetCastData(AgentItem.InstID)) { if (!(c.Time >= minTime)) { continue; } ParseEnum.StateChange state = c.IsStateChange; if (state == ParseEnum.StateChange.Normal) { if (c.IsActivation.IsCasting() && c.Time <= maxTime) { long time = log.FightData.ToFightSpace(c.Time); curCastLog = new CastLog(time, c.SkillID, c.Value, c.IsActivation); CastLogs.Add(curCastLog); } else { if (curCastLog != null) { if (curCastLog.SkillId == c.SkillID) { curCastLog.SetEndStatus(c.Value, c.IsActivation, log.FightData.FightDuration); curCastLog = null; } } } } } }
protected override void SetCastLogs(ParsedLog log) { long agentStart = Math.Max(FirstAware, log.FightData.FightStart); long agentEnd = Math.Min(LastAware, log.FightData.FightEnd); long timeStart = log.FightData.FightStart; CastLog curCastLog = null; foreach (CombatItem c in log.GetCastData(AgentItem.InstID)) { if (!(c.Time > agentStart)) { continue; } ParseEnum.StateChange state = c.IsStateChange; if (state == ParseEnum.StateChange.Normal) { if (c.IsActivation.IsCasting() && c.Time < agentEnd) { long time = c.Time - timeStart; curCastLog = new CastLog(time, c.SkillID, c.Value, c.IsActivation); CastLogs.Add(curCastLog); } else { if (curCastLog != null) { if (curCastLog.SkillId == c.SkillID) { curCastLog.SetEndStatus(c.Value, c.IsActivation); curCastLog = null; } } } } else if (state == ParseEnum.StateChange.WeaponSwap && c.Time < agentEnd) { long time = c.Time - timeStart; CastLog swapLog = new CastLog(time, SkillItem.WeaponSwapId, (int)c.DstAgent, c.IsActivation); CastLogs.Add(swapLog); } } }
protected virtual void SetCastLogs(ParsedLog log) { CastLog curCastLog = null; foreach (CombatItem c in log.GetCastData(InstID, FirstAware, LastAware)) { ParseEnum.StateChange state = c.IsStateChange; if (state == ParseEnum.StateChange.Normal) { if (c.IsActivation.StartCasting()) { // Missing end activation long time = log.FightData.ToFightSpace(c.Time); if (curCastLog != null) { int actDur = curCastLog.SkillId == SkillItem.DodgeId ? 750 : curCastLog.ExpectedDuration; curCastLog.SetEndStatus(actDur, ParseEnum.Activation.Unknown, time); curCastLog = null; } curCastLog = new CastLog(time, c.SkillID, c.Value, c.IsActivation, Agent, InstID); CastLogs.Add(curCastLog); } else { if (curCastLog != null) { if (curCastLog.SkillId == c.SkillID) { int actDur = curCastLog.SkillId == SkillItem.DodgeId ? 750 : c.Value; curCastLog.SetEndStatus(actDur, c.IsActivation, log.FightData.FightDuration); curCastLog = null; } } } } else if (state == ParseEnum.StateChange.WeaponSwap) { long time = log.FightData.ToFightSpace(c.Time); CastLog swapLog = new CastLog(time, SkillItem.WeaponSwapId, (int)c.DstAgent, c.IsActivation, Agent, InstID); if (CastLogs.Count > 0 && (time - CastLogs.Last().Time) < 10 && CastLogs.Last().SkillId == SkillItem.WeaponSwapId) { CastLogs[CastLogs.Count - 1] = swapLog; } else { CastLogs.Add(swapLog); } swapLog.SetEndStatus(50, ParseEnum.Activation.Unknown, log.FightData.FightDuration); } } long cloakStart = 0; foreach (long time in log.CombatData.GetBuffs(InstID, 40408, FirstAware, LastAware).Select(x => log.FightData.ToFightSpace(x.Time))) { if (time - cloakStart > 10) { CastLog dodgeLog = new CastLog(time, SkillItem.DodgeId, 0, ParseEnum.Activation.Unknown, Agent, InstID); dodgeLog.SetEndStatus(50, ParseEnum.Activation.Unknown, log.FightData.FightDuration); CastLogs.Add(dodgeLog); } cloakStart = time; } CastLogs.Sort((x, y) => x.Time.CompareTo(y.Time)); }
public void ComputeMechanics(ParsedLog log) { MechanicData mechData = log.MechanicData; FightData fightData = log.FightData; CombatData combatData = log.CombatData; long start = fightData.FightStart; long end = fightData.FightEnd; Mechanic.CheckSpecialCondition condition; HashSet <ushort> playersIds = new HashSet <ushort>(log.PlayerList.Select(x => x.InstID)); Dictionary <ushort, AbstractMasterPlayer> regroupedMobs = new Dictionary <ushort, AbstractMasterPlayer>(); foreach (Mechanic mech in MechanicList) { switch (mech.MechanicType) { case Mechanic.MechType.PlayerStatus: foreach (Player p in log.PlayerList) { List <CombatItem> cList = new List <CombatItem>(); switch (mech.SkillId) { case SkillItem.DeathId: cList = combatData.GetStates(p.InstID, ParseEnum.StateChange.ChangeDead, start, end); break; case SkillItem.DownId: cList = combatData.GetStates(p.InstID, ParseEnum.StateChange.ChangeDown, start, end); break; case SkillItem.ResurrectId: cList = log.GetCastData(p.InstID).Where(x => x.SkillID == SkillItem.ResurrectId && x.IsActivation.IsCasting()).ToList(); break; } foreach (CombatItem mechItem in cList) { mechData[mech].Add(new MechanicLog(mechItem.Time - start, mech, p)); } } break; case Mechanic.MechType.SkillOnPlayer: foreach (Player p in log.PlayerList) { List <DamageLog> dls = p.GetDamageTakenLogs(log, 0, fightData.FightDuration); condition = mech.SpecialCondition; foreach (DamageLog dLog in dls) { if (condition != null && !condition(new SpecialConditionItem(dLog))) { continue; } if (dLog.SkillId == mech.SkillId && dLog.Result.IsHit()) { mechData[mech].Add(new MechanicLog(dLog.Time, mech, p)); } } } break; case Mechanic.MechType.PlayerBoon: case Mechanic.MechType.PlayerOnPlayer: case Mechanic.MechType.PlayerBoonRemove: foreach (Player p in log.PlayerList) { condition = mech.SpecialCondition; foreach (CombatItem c in log.GetBoonData(mech.SkillId)) { if (condition != null && !condition(new SpecialConditionItem(c))) { continue; } if (mech.MechanicType == Mechanic.MechType.PlayerBoonRemove) { if (c.IsBuffRemove == ParseEnum.BuffRemove.Manual && p.InstID == c.SrcInstid) { mechData[mech].Add(new MechanicLog(c.Time - start, mech, p)); } } else { if (c.IsBuffRemove == ParseEnum.BuffRemove.None && p.InstID == c.DstInstid) { mechData[mech].Add(new MechanicLog(c.Time - start, mech, p)); if (mech.MechanicType == Mechanic.MechType.PlayerOnPlayer) { mechData[mech].Add(new MechanicLog(c.Time - start, mech, log.PlayerList.FirstOrDefault(x => x.InstID == c.SrcInstid))); } } } } } break; case Mechanic.MechType.HitOnEnemy: foreach (Player p in log.PlayerList) { condition = mech.SpecialCondition; IEnumerable <AgentItem> agents = log.AgentData.GetAgentsByID((ushort)mech.SkillId); foreach (AgentItem a in agents) { foreach (DamageLog dl in p.GetDamageLogs(null, log, 0, log.FightData.FightDuration)) { if (dl.DstInstId != a.InstID || dl.IsCondi > 0 || dl.Time < a.FirstAware - start || dl.Time > a.LastAware - start || (condition != null && !condition(new SpecialConditionItem(dl)))) { continue; } mechData[mech].Add(new MechanicLog(dl.Time, mech, p)); } } } break; case Mechanic.MechType.PlayerSkill: foreach (Player p in log.PlayerList) { condition = mech.SpecialCondition; foreach (CombatItem c in log.GetCastDataById(mech.SkillId)) { if (condition != null && !condition(new SpecialConditionItem(c))) { continue; } if (c.IsActivation.IsCasting() && c.SrcInstid == p.InstID) { mechData[mech].Add(new MechanicLog(c.Time - fightData.FightStart, mech, p)); } } } break; case Mechanic.MechType.EnemyBoon: case Mechanic.MechType.EnemyBoonStrip: condition = mech.SpecialCondition; foreach (CombatItem c in log.GetBoonData(mech.SkillId)) { if (condition != null && !condition(new SpecialConditionItem(c))) { continue; } AbstractMasterPlayer amp = null; if (mech.MechanicType == Mechanic.MechType.EnemyBoon && c.IsBuffRemove == ParseEnum.BuffRemove.None) { Boss target = Targets.Find(x => x.InstID == c.DstInstid && x.FirstAware <= c.Time && x.LastAware >= c.Time); if (target != null) { amp = target; } else { AgentItem a = log.AgentData.GetAgent(c.DstAgent); if (playersIds.Contains(a.InstID)) { continue; } else if (a.MasterAgent != 0) { AgentItem m = log.AgentData.GetAgent(a.MasterAgent); if (playersIds.Contains(m.InstID)) { continue; } } if (!regroupedMobs.TryGetValue(a.ID, out amp)) { amp = new DummyPlayer(a); regroupedMobs.Add(a.ID, amp); } } } else if (mech.MechanicType == Mechanic.MechType.EnemyBoonStrip && c.IsBuffRemove == ParseEnum.BuffRemove.Manual) { Boss target = Targets.Find(x => x.InstID == c.SrcInstid && x.FirstAware <= c.Time && x.LastAware >= c.Time); if (target != null) { amp = target; } else { AgentItem a = log.AgentData.GetAgent(c.SrcAgent); if (playersIds.Contains(a.InstID)) { continue; } else if (a.MasterAgent != 0) { AgentItem m = log.AgentData.GetAgent(a.MasterAgent); if (playersIds.Contains(m.InstID)) { continue; } } if (!regroupedMobs.TryGetValue(a.ID, out amp)) { amp = new DummyPlayer(a); regroupedMobs.Add(a.ID, amp); } } } if (amp != null) { mechData[mech].Add(new MechanicLog(c.Time - fightData.FightStart, mech, amp)); } } break; case Mechanic.MechType.EnemyCastEnd: case Mechanic.MechType.EnemyCastStart: condition = mech.SpecialCondition; foreach (CombatItem c in log.GetCastDataById(mech.SkillId)) { if (condition != null && !condition(new SpecialConditionItem(c))) { continue; } AbstractMasterPlayer amp = null; if ((mech.MechanicType == Mechanic.MechType.EnemyCastStart && c.IsActivation.IsCasting()) || (mech.MechanicType == Mechanic.MechType.EnemyCastEnd && !c.IsActivation.IsCasting())) { Boss target = Targets.Find(x => x.InstID == c.SrcInstid && x.FirstAware <= c.Time && x.LastAware >= c.Time); if (target != null) { amp = target; } else { AgentItem a = log.AgentData.GetAgent(c.SrcAgent); if (playersIds.Contains(a.InstID)) { continue; } else if (a.MasterAgent != 0) { AgentItem m = log.AgentData.GetAgent(a.MasterAgent); if (playersIds.Contains(m.InstID)) { continue; } } if (!regroupedMobs.TryGetValue(a.ID, out amp)) { amp = new DummyPlayer(a); regroupedMobs.Add(a.ID, amp); } } } if (amp != null) { mechData[mech].Add(new MechanicLog(c.Time - fightData.FightStart, mech, amp)); } } break; case Mechanic.MechType.Spawn: foreach (AgentItem a in log.AgentData.GetAgentByType(AgentItem.AgentType.NPC).Where(x => x.ID == mech.SkillId)) { if (!regroupedMobs.TryGetValue(a.ID, out AbstractMasterPlayer amp)) { amp = new DummyPlayer(a); regroupedMobs.Add(a.ID, amp); } mechData[mech].Add(new MechanicLog(a.FirstAware - fightData.FightStart, mech, amp)); } break; } } mechData.ComputePresentMechanics(log); }