コード例 #1
0
 private NetworkController()
 {
     TeraSniffer.Instance.NewConnection += HandleNewConnection;
     AbnormalityStorage = new AbnormalityStorage();
     var packetAnalysis = new Thread(PacketAnalysisLoop);
     packetAnalysis.Start();
 }
コード例 #2
0
        public void Update(EntityInformation entityInformation, AbnormalityStorage abnormals)
        {
            EnduranceAbnormality.Items.Clear();
            if (entityInformation == null)
            {
                return;
            }
            if (entityInformation.Interval == 0)
            {
                return;
            }

            EnduranceAbnormality.Items.Add(_header);

            var count = 0;

            foreach (var abnormality in abnormals.Get(entityInformation.Entity))
            {
                EnduranceDebuff abnormalityUi;
                if (_enduranceDebuffsList.Count > count)
                {
                    abnormalityUi = _enduranceDebuffsList[count];
                }
                else
                {
                    abnormalityUi = new EnduranceDebuff();
                    _enduranceDebuffsList.Add(abnormalityUi);
                }

                abnormalityUi.Update(abnormality.Key, abnormality.Value, entityInformation.BeginTime, entityInformation.EndTime);
                EnduranceAbnormality.Items.Add(abnormalityUi);
                count++;
            }
        }
コード例 #3
0
        public static void ManualExport(NpcEntity entity, AbnormalityStorage abnormality, Dest type)
        {
            if (entity == null)
            {
                return;
            }
            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }
            var sendThread = new Thread(() =>
            {
                if (type.HasFlag(Dest.Site) && PacketProcessor.Instance.BossLink.Any(x => x.Value == entity && x.Key.StartsWith("!")))
                {
                    DpsServers.Where(x => PacketProcessor.Instance.BossLink.Where(y => y.Value == entity && y.Key.StartsWith("!"))
                                     .Select(y => y.Key.Substring(1, y.Key.IndexOf(" ", StringComparison.Ordinal) - 1))
                                     .Contains(x.Guid.ToString())).ToList().ForEach(x => x.CheckAndSendFightData(stats.BaseStats, entity));
                }
                if (type.HasFlag(Dest.Excel))
                {
                    ExcelExporter.ExcelSave(stats,
                                            stats.BaseStats.members.Select(x => x.playerName)
                                            .FirstOrDefault(x => PacketProcessor.Instance.MeterPlayers.Select(z => z.Name).Contains(x)), type.HasFlag(Dest.Manual));
                }
            });

            sendThread.Start();
        }
コード例 #4
0
 public static void CopyThread(StatsSummary stats, Skills skills, AbnormalityStorage abnormals,
                               bool timedEncounter, CopyKey copy)
 {
     if (BasicTeraData.Instance.HotDotDatabase == null)
     {
         return;                                               //no database loaded yet => no need to do anything
     }
     lock (_pasteLock)
     {
         var text = CopyPaste.Copy(stats, skills, abnormals, timedEncounter, copy);
         for (var i = 0; i < 3; i++)
         {
             try
             {
                 Clipboard.SetText(text.Item2);
                 break;
             }
             catch
             {
                 Thread.Sleep(100);
                 //Ignore
             }
         }
         CopyPaste.Paste(text.Item1);
     }
 }
コード例 #5
0
        public void Update(EntityInformation entityInformation, AbnormalityStorage abnormals)
        {
            EnduranceAbnormality.Items.Clear();
            if (entityInformation == null)
            {
                return;
            }
            if (entityInformation.Interval == 0)
            {
                return;
            }

            EnduranceAbnormality.Items.Add(_header);

            var count = 0;
            foreach (var abnormality in abnormals.Get(entityInformation.Entity))
            {
                EnduranceDebuff abnormalityUi;
                if (_enduranceDebuffsList.Count > count)
                {
                    abnormalityUi = _enduranceDebuffsList[count];
                }
                else
                {
                    abnormalityUi = new EnduranceDebuff();
                    _enduranceDebuffsList.Add(abnormalityUi);
                }

                abnormalityUi.Update(abnormality.Key, abnormality.Value,
                    entityInformation.BeginTime,
                    entityInformation.EndTime);
                EnduranceAbnormality.Items.Add(abnormalityUi);
                count++;
            }
        }
コード例 #6
0
        public static void ManualExport(NpcEntity entity, AbnormalityStorage abnormality, Dest type)
        {
            if (entity == null)
            {
                return;
            }
            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }
            var name = stats.BaseStats.members.Select(x => x.playerName).FirstOrDefault(x => PacketProcessor.Instance.MeterPlayers.Select(z => z.Name).Contains(x));

            if (type.HasFlag(Dest.Json))
            {
                JsonExporter.JsonSave(stats, name, type.HasFlag(Dest.Manual));
            }
            var sendThread = new Thread(() =>
            {
                if (type.HasFlag(Dest.Site) && PacketProcessor.Instance.BossLink.Any(x => x.Value == entity && !x.Key.Success))
                {
                    DpsServers.Where(x => PacketProcessor.Instance.BossLink.Where(y => y.Value == entity && !y.Key.Success)
                                     .Select(y => y.Key.Server)
                                     .Contains(x.Data.HostName)).ToList().ForEach(x => x.CheckAndSendFightData(stats.BaseStats, entity));
                }
                if (type.HasFlag(Dest.Excel))
                {
                    ExcelExporter.ExcelSave(stats, name, type.HasFlag(Dest.Manual));
                }
            });

            sendThread.Start();
        }
コード例 #7
0
        public static void AutomatedExport(NpcEntity entity, AbnormalityStorage abnormality)
        {
            if (entity == null)
            {
                return;
            }
            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }
            JsonExporter.JsonSave(stats, PacketProcessor.Instance.EntityTracker.MeterUser.Name);
            var sendThread = new Thread(() =>
            {
                DpsServers.Where(x => !x.AnonymousUpload).ToList().ForEach(x => x.CheckAndSendFightData(stats.BaseStats, entity));
                ExcelExporter.ExcelSave(stats, PacketProcessor.Instance.EntityTracker.MeterUser.Name);
                Anonymize(stats.BaseStats);
                DpsServers.Where(x => x.AnonymousUpload).ToList().ForEach(x => x.CheckAndSendFightData(stats.BaseStats, entity));
                if (BasicTeraData.Instance.WindowData.PacketsCollect)
                {
                    try
                    {
                        PacketsExporter.Instance.Export(stats.BaseStats, entity);
                    }
                    catch (Exception ex)
                    {
                        BasicTeraData.LogError("##### Packets export EXCEPTION #####\r\n" + ex.Message + "\r\n" + ex.StackTrace + "\r\n" + ex.Source + "\r\n" + ex + "\r\n" + ex.Data +
                                               "\r\n" + ex.InnerException + "\r\n" + ex.TargetSite);
                    }
                }
            });

            sendThread.Start();
        }
コード例 #8
0
        public static void ManualExport(NpcEntity entity, AbnormalityStorage abnormality, Dest type)
        {
            if (entity == null)
            {
                return;
            }
            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }
            var sendThread = new Thread(() =>
            {
                if (type.HasFlag(Dest.Site) && NetworkController.Instance.BossLink.Any(x => x.Value == entity && x.Key.StartsWith("!0")))
                {
                    ToTeraDpsApi(stats.BaseStats, entity);
                }
                if (type.HasFlag(Dest.Site) && NetworkController.Instance.BossLink.Any(x => x.Value == entity && x.Key.StartsWith("!") && !x.Key.StartsWith("!0")))
                {
                    ToPrivateServer(stats.BaseStats, entity, NetworkController.Instance.BossLink.Where(x => x.Value == entity && x.Key.StartsWith("!") && !x.Key.StartsWith("!0")).Select(x => int.Parse(x.Key.Substring(1, x.Key.IndexOf(" ") - 1))).ToList());
                }
                if (type.HasFlag(Dest.Excel))
                {
                    ExcelExport.ExcelSave(stats, stats.BaseStats.members.Select(x => x.playerName).FirstOrDefault(x => NetworkController.Instance.MeterPlayers.Select(z => z.Name).Contains(x)), type.HasFlag(Dest.Manual));
                }
            });

            sendThread.Start();
        }
コード例 #9
0
        private NetworkController()
        {
            TeraSniffer.Instance.NewConnection += HandleNewConnection;
            _abnormalityStorage = new AbnormalityStorage();
            var packetAnalysis = new Thread(PacketAnalysisLoop);

            packetAnalysis.Start();
        }
コード例 #10
0
 public AbnormalityTracker(EntityTracker entityTracker, PlayerTracker playerTracker,
                           HotDotDatabase hotDotDatabase, AbnormalityStorage abnormalityStorage, Action <SkillResult> update = null)
 {
     EntityTracker       = entityTracker;
     PlayerTracker       = playerTracker;
     HotDotDatabase      = hotDotDatabase;
     UpdateDamageTracker = update;
     AbnormalityStorage  = abnormalityStorage;
 }
コード例 #11
0
        private PacketProcessor()
        {
            TeraSniffer.Instance.NewConnection += HandleNewConnection;
            TeraSniffer.Instance.EndConnection += HandleEndConnection;
            AbnormalityStorage = new AbnormalityStorage();
            var packetAnalysis = new Thread(PacketAnalysisLoop);

            packetAnalysis.Start();
            TeraSniffer.Instance.EnableMessageStorage = BasicTeraData.Instance.WindowData.PacketsCollect;
        }
コード例 #12
0
        public static void AutomatedExport(SDespawnNpc despawnNpc, AbnormalityStorage abnormality)
        {
            if (!despawnNpc.Dead)
            {
                return;
            }

            var entity = (NpcEntity)DamageTracker.Instance.GetEntity(despawnNpc.Npc);

            AutomatedExport(entity, abnormality);
        }
コード例 #13
0
 public UiUpdateMessage(StatsSummary statsSummary, Skills skills, List<NpcEntity> entities, bool timedEncounter,
     AbnormalityStorage abnormals, ConcurrentDictionary<UploadData, NpcEntity> bossHistory, List<ChatMessage> chatbox,
      List<NotifyFlashMessage> flash)
 {
     StatsSummary = statsSummary;
     Skills = skills;
     Entities = entities;
     TimedEncounter = timedEncounter;
     Abnormals = abnormals;
     BossHistory = bossHistory;
     Chatbox = chatbox;
     Flash = flash;
 }
コード例 #14
0
        public static void Export(SDespawnNpc despawnNpc, AbnormalityStorage abnormality)
        {
            var stats = GenerateStats(despawnNpc, abnormality);

            if (stats == null)
            {
                return;
            }
            var sendThread = new Thread(() => {
                ToTeraDpsApi(stats.BaseStats, despawnNpc);
                ExcelExport.ExcelSave(stats);
                ToAnonymousStatistics(stats.BaseStats);
            });

            sendThread.Start();
        }
コード例 #15
0
ファイル: DataExporter.cs プロジェクト: neowutran/ShinraMeter
 public static void Export(NpcEntity entity, AbnormalityStorage abnormality, Dest type)
 {
     if (entity==null) return;
     var stats = GenerateStats(entity, abnormality);
     if (stats == null)
     {
         return;
     }
     var sendThread = new Thread(() =>
     {
         if ((type&Dest.Site)!=0 && NetworkController.Instance.BossLink.Any(x=>x.Value==entity&&x.Key.StartsWith("!")))
             ToTeraDpsApi(stats.BaseStats, entity);
         if ((type&Dest.Excel)!=0)
             ExcelExport.ExcelSave(stats);
     });
     sendThread.Start();
 }
コード例 #16
0
ファイル: DataExporter.cs プロジェクト: neowutran/ShinraMeter
        public static void Export(SDespawnNpc despawnNpc, AbnormalityStorage abnormality)
        {
            if (!despawnNpc.Dead) return;

            var entity = (NpcEntity)DamageTracker.Instance.GetEntity(despawnNpc.Npc);
            if (entity==null) return;// killing mob spawned by missed packet
            var stats = GenerateStats(entity, abnormality);
            if (stats == null)
            {
                return;
            }
            var sendThread = new Thread(() =>
            {
                ToTeraDpsApi(stats.BaseStats, entity);
                ExcelExport.ExcelSave(stats, NetworkController.Instance.EntityTracker.MeterUser.Name);
                ToAnonymousStatistics(stats.BaseStats);
            });
            sendThread.Start();
        }
コード例 #17
0
ファイル: DataExporter.cs プロジェクト: stas2130/ShinraMeter
        public static void Export(NpcEntity entity, AbnormalityStorage abnormality)
        {
            if (entity == null)
            {
                return;
            }
            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }
            var sendThread = new Thread(() =>
            {
                ExcelExport.ExcelSave(stats);
            });

            sendThread.Start();
        }
コード例 #18
0
        public void Update(Dictionary <Entity, EntityInfo> stats, AbnormalityStorage abnormals, Entity currentBoss)
        {
            var entity = currentBoss;

            EnduranceAbnormality.Items.Clear();
            if (entity == null)
            {
                return;
            }
            var statsAbnormalities = stats[entity];

            if (statsAbnormalities.Interval == 0 || entity.NpcE == null)
            {
                return;
            }

            EnduranceAbnormality.Items.Add(_header);

            var count = 0;

            foreach (var abnormality in abnormals.Get(entity.NpcE))
            {
                EnduranceDebuff abnormalityUi;
                if (_enduranceDebuffsList.Count > count)
                {
                    abnormalityUi = _enduranceDebuffsList[count];
                }
                else
                {
                    abnormalityUi = new EnduranceDebuff();
                    _enduranceDebuffsList.Add(abnormalityUi);
                }

                abnormalityUi.Update(abnormality.Key, abnormality.Value,
                                     statsAbnormalities.FirstHit / TimeSpan.TicksPerSecond,
                                     statsAbnormalities.LastHit / TimeSpan.TicksPerSecond);
                EnduranceAbnormality.Items.Add(abnormalityUi);
                count++;
            }
        }
コード例 #19
0
 private void Pause(bool reset = true)
 {
     PacketProcessing.Pause();
     if (reset)
     {
         Database.Database.Instance.DeleteAll();
         AbnormalityStorage = new AbnormalityStorage();
         AbnormalityTracker = new AbnormalityTracker(EntityTracker, PlayerTracker, BasicTeraData.Instance.HotDotDatabase, AbnormalityStorage, DamageTracker.Instance.Update);
         if (MessageFactory.ChatEnabled)
         {
             AbnormalityTracker.AbnormalityAdded   += NotifyProcessor.Instance.AbnormalityNotifierAdded;
             AbnormalityTracker.AbnormalityRemoved += NotifyProcessor.Instance.AbnormalityNotifierRemoved;
         }
     }
     else
     {
         AbnormalityStorage.EndAll(DateTime.UtcNow.Ticks);
     }
     TeraSniffer.Instance.Packets = new ConcurrentQueue <Message>();
     HudManager.Instance.CurrentBosses.DisposeAll();
     NotifyProcessor.Instance.S_LOAD_TOPO(null);
 }
コード例 #20
0
        public static void AutomatedExport(NpcEntity entity, AbnormalityStorage abnormality)
        {
            if (entity == null)
            {
                return;
            }
            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }

            var sendThread = new Thread(() =>
            {
                ToTeraDpsApi(stats.BaseStats, entity);
                ToPrivateServer(stats.BaseStats, entity);
                ExcelExport.ExcelSave(stats, NetworkController.Instance.EntityTracker.MeterUser.Name);
                ToAnonymousStatistics(stats.BaseStats);
            });

            sendThread.Start();
        }
コード例 #21
0
ファイル: DataExporter.cs プロジェクト: solver07/ShinraMeter
        public static void AutomatedExport(NpcEntity entity, AbnormalityStorage abnormality)
        {
            if (entity == null)
            {
                return;
            }
            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }

            var sendThread = new Thread(() =>
            {
                DpsServers.Where(x => !x.AnonymousUpload).ToList().ForEach(x => x.CheckAndSendFightData(stats.BaseStats, entity));
                ExcelExport.ExcelSave(stats, NetworkController.Instance.EntityTracker.MeterUser.Name);
                Anonymize(stats.BaseStats);
                DpsServers.Where(x => x.AnonymousUpload).ToList().ForEach(x => x.CheckAndSendFightData(stats.BaseStats, entity));
            });

            sendThread.Start();
        }
コード例 #22
0
ファイル: DataExporter.cs プロジェクト: stas2130/ShinraMeter
        public static void Export(SDespawnNpc despawnNpc, AbnormalityStorage abnormality)
        {
            if (!despawnNpc.Dead)
            {
                return;
            }

            var entity = (NpcEntity)DamageTracker.Instance.GetEntity(despawnNpc.Npc);

            var stats = GenerateStats(entity, abnormality);

            if (stats == null)
            {
                return;
            }
            var sendThread = new Thread(() =>
            {
                ToTeraDpsApi(stats.BaseStats, despawnNpc);
                ExcelExport.ExcelSave(stats, NetworkController.Instance.EntityTracker.MeterUser.Name);
                ToAnonymousStatistics(stats.BaseStats);
            });

            sendThread.Start();
        }
コード例 #23
0
        private static ExtendedStats GenerateStats(NpcEntity entity, AbnormalityStorage abnormals)
        {
            if (!entity.Info.Boss)
            {
                return(null);
            }

            var timedEncounter = false;

            /*
             * modify timedEncounter depending on teradps.io need
             *
             */

            var entityInfo  = Database.Database.Instance.GlobalInformationEntity(entity, timedEncounter);
            var skills      = Database.Database.Instance.GetSkills(entityInfo.BeginTime, entityInfo.EndTime);
            var playersInfo = timedEncounter
                ? Database.Database.Instance.PlayerDamageInformation(entityInfo.BeginTime, entityInfo.EndTime)
                : Database.Database.Instance.PlayerDamageInformation(entity);
            var heals = Database.Database.Instance.PlayerHealInformation(entityInfo.BeginTime, entityInfo.EndTime);

            playersInfo.RemoveAll(x => x.Amount == 0);

            var firstTick = entityInfo.BeginTime;
            var lastTick  = entityInfo.EndTime;
            var interTick = lastTick - firstTick;
            var interval  = interTick / TimeSpan.TicksPerSecond;

            if (interval == 0)
            {
                return(null);
            }
            var totaldamage = entityInfo.TotalDamage;
            var partyDps    = TimeSpan.TicksPerSecond * totaldamage / interTick;

            var teradpsData   = new EncounterBase();
            var extendedStats = new ExtendedStats();
            var _abnormals    = abnormals.Clone(entity, firstTick, lastTick);

            teradpsData.encounterUnixEpoch = new DateTimeOffset(new DateTime(lastTick, DateTimeKind.Utc)).ToUnixTimeSeconds();
            extendedStats.Entity           = entity;
            extendedStats.BaseStats        = teradpsData;
            extendedStats.FirstTick        = firstTick;
            extendedStats.LastTick         = lastTick;
            teradpsData.areaId             = entity.Info.HuntingZoneId + "";
            teradpsData.bossId             = entity.Info.TemplateId + "";
            teradpsData.fightDuration      = interval + "";
            teradpsData.partyDps           = partyDps + "";
            extendedStats.Debuffs          = _abnormals.Get(entity);

            foreach (var debuff in extendedStats.Debuffs.OrderByDescending(x => x.Value.Duration(firstTick, lastTick)))
            {
                var percentage = debuff.Value.Duration(firstTick, lastTick) * 100 / interTick;
                if (percentage == 0)
                {
                    continue;
                }
                teradpsData.debuffUptime.Add(new KeyValuePair <string, string>(
                                                 debuff.Key.Id + "", percentage + ""
                                                 ));
                var stacks = new List <List <int> > {
                    new List <int> {
                        0, (int)percentage
                    }
                };
                var stackList = debuff.Value.Stacks(firstTick, lastTick).OrderBy(x => x);
                teradpsData.debuffDetail.Add(new List <object> {
                    debuff.Key.Id, stacks
                });
                if (stackList.Any() && stackList.Max() == 1)
                {
                    continue;
                }
                foreach (var stack in stackList)
                {
                    percentage = debuff.Value.Duration(firstTick, lastTick, stack) * 100 / interTick;
                    if (percentage == 0)
                    {
                        continue;
                    }
                    stacks.Add(new List <int> {
                        stack, (int)percentage
                    });
                }
            }

            foreach (var user in playersInfo.OrderByDescending(x => x.Amount))
            {
                var teradpsUser = new Members();
                var damage      = user.Amount;
                teradpsUser.playerTotalDamage = damage + "";

                if (damage <= 0)
                {
                    continue;
                }

                var buffs = _abnormals.Get(user.Source);
                teradpsUser.guild                 = string.IsNullOrWhiteSpace(user.Source.GuildName) ? null : user.Source.GuildName;
                teradpsUser.playerClass           = user.Source.Class.ToString();
                teradpsUser.playerName            = user.Source.Name;
                teradpsUser.playerId              = user.Source.PlayerId;
                teradpsUser.playerServer          = BasicTeraData.Instance.Servers.GetServerName(user.Source.ServerId);
                teradpsUser.playerAverageCritRate = Math.Round(user.CritRate, 1) + "";
                teradpsUser.healCrit              = user.Source.IsHealer
                    ? heals.FirstOrDefault(x => x.Source == user.Source)?.CritRate + ""
                    : null;
                teradpsUser.playerDps = TimeSpan.TicksPerSecond * damage / interTick + "";
                teradpsUser.playerTotalDamagePercentage = user.Amount * 100 / entityInfo.TotalDamage + "";

                extendedStats.PlayerReceived.Add(user.Source.Name, Tuple.Create(skills.HitsReceived(user.Source.User, entity, timedEncounter), skills.DamageReceived(user.Source.User, entity, timedEncounter)));
                extendedStats.PlayerCritDamageRate.Add(user.Source.Name, user.CritDamageRate);

                var death = buffs.Death;
                teradpsUser.playerDeaths        = death.Count(firstTick, lastTick) + "";
                teradpsUser.playerDeathDuration = death.Duration(firstTick, lastTick) / TimeSpan.TicksPerSecond + "";

                var aggro = buffs.Aggro(entity);
                teradpsUser.aggro = 100 * aggro.Duration(firstTick, lastTick) / interTick + "";

                foreach (var buff in buffs.Times.OrderByDescending(x => x.Value.Duration(firstTick, lastTick)))
                {
                    var percentage = buff.Value.Duration(firstTick, lastTick) * 100 / interTick;
                    if (percentage == 0)
                    {
                        continue;
                    }
                    teradpsUser.buffUptime.Add(new KeyValuePair <string, string>(
                                                   buff.Key.Id + "", percentage + ""
                                                   ));
                    var stacks = new List <List <int> > {
                        new List <int> {
                            0, (int)percentage
                        }
                    };
                    var stackList = buff.Value.Stacks(firstTick, lastTick).OrderBy(x => x);
                    teradpsUser.buffDetail.Add(new List <object> {
                        buff.Key.Id, stacks
                    });
                    if (stackList.Any() && stackList.Max() == 1)
                    {
                        continue;
                    }
                    foreach (var stack in buff.Value.Stacks(firstTick, lastTick).OrderBy(x => x))
                    {
                        percentage = buff.Value.Duration(firstTick, lastTick, stack) * 100 / interTick;
                        if (percentage == 0)
                        {
                            continue;
                        }
                        stacks.Add(new List <int> {
                            stack, (int)percentage
                        });
                    }
                }
                var serverPlayerName = $"{teradpsUser.playerServer}_{teradpsUser.playerName}";
                extendedStats.PlayerSkills.Add(serverPlayerName,
                                               skills.GetSkillsDealt(user.Source.User, entity, timedEncounter));
                extendedStats.PlayerBuffs.Add(serverPlayerName, buffs);

                var skillsId = SkillAggregate.GetAggregate(user, entityInfo.Entity, skills, timedEncounter, Database.Database.Type.Damage);
                extendedStats.PlayerSkillsAggregated[teradpsUser.playerServer + "/" + teradpsUser.playerName] = skillsId;

                foreach (var skill in skillsId.OrderByDescending(x => x.Amount()))
                {
                    var skillLog    = new SkillLog();
                    var skilldamage = skill.Amount();

                    skillLog.skillAverageCrit   = Math.Round(skill.AvgCrit()) + "";
                    skillLog.skillAverageWhite  = Math.Round(skill.AvgWhite()) + "";
                    skillLog.skillCritRate      = skill.CritRate() + "";
                    skillLog.skillDamagePercent = skill.DamagePercent() + "";
                    skillLog.skillHighestCrit   = skill.BiggestCrit() + "";
                    skillLog.skillHits          = skill.Hits() + "";
                    var skillKey = skill.Skills.First().Key;
                    skillLog.skillId          = BasicTeraData.Instance.SkillDatabase.GetSkillByPetName(skillKey.NpcInfo?.Name, user.Source.RaceGenderClass)?.Id.ToString() ?? skillKey.Id.ToString();
                    skillLog.skillLowestCrit  = skill.LowestCrit() + "";
                    skillLog.skillTotalDamage = skilldamage + "";


                    if (skilldamage == 0)
                    {
                        continue;
                    }
                    teradpsUser.skillLog.Add(skillLog);
                }
                if (NetworkController.Instance.MeterPlayers.Contains(user.Source))
                {
                    teradpsData.uploader = teradpsData.members.Count.ToString();
                }
                teradpsData.members.Add(teradpsUser);
            }
            return(extendedStats);
        }
コード例 #24
0
ファイル: DataExporter.cs プロジェクト: neowutran/ShinraMeter
        private static ExtendedStats GenerateStats(NpcEntity entity, AbnormalityStorage abnormals)
        {
            if (!entity.Info.Boss) return null;

            var timedEncounter = false;

            /*
              modify timedEncounter depending on teradps.io need

            */

            var entityInfo = Database.Database.Instance.GlobalInformationEntity(entity, timedEncounter);
            var skills = Database.Database.Instance.GetSkills(entityInfo.BeginTime, entityInfo.EndTime);
            var playersInfo = timedEncounter
                ? Database.Database.Instance.PlayerDamageInformation(entityInfo.BeginTime, entityInfo.EndTime)
                : Database.Database.Instance.PlayerDamageInformation(entity);
            var heals = Database.Database.Instance.PlayerHealInformation(entityInfo.BeginTime, entityInfo.EndTime);
            playersInfo.RemoveAll(x => x.Amount == 0);

            var firstTick = entityInfo.BeginTime;
            var lastTick = entityInfo.EndTime;
            var interTick = lastTick - firstTick;
            var interval = interTick/TimeSpan.TicksPerSecond;
            if (interval == 0)
            {
                return null;
            }
            var totaldamage = entityInfo.TotalDamage;
            var partyDps = TimeSpan.TicksPerSecond*totaldamage/interTick;

            var teradpsData = new EncounterBase();
            var extendedStats = new ExtendedStats();
            var _abnormals = abnormals.Clone(entity, firstTick, lastTick);
            teradpsData.encounterUnixEpoch = new DateTimeOffset(new DateTime(lastTick,DateTimeKind.Utc)).ToUnixTimeSeconds();
            extendedStats.Entity = entity;
            extendedStats.BaseStats = teradpsData;
            extendedStats.FirstTick = firstTick;
            extendedStats.LastTick = lastTick;
            teradpsData.areaId = entity.Info.HuntingZoneId + "";
            teradpsData.bossId = entity.Info.TemplateId + "";
            teradpsData.fightDuration = interval + "";
            teradpsData.partyDps = partyDps + "";
            extendedStats.Debuffs = _abnormals.Get(entity);

            foreach (var debuff in extendedStats.Debuffs.OrderByDescending(x => x.Value.Duration(firstTick, lastTick)))
            {
                var percentage = debuff.Value.Duration(firstTick, lastTick)*100/interTick;
                if (percentage == 0)
                {
                    continue;
                }
                teradpsData.debuffUptime.Add(new KeyValuePair<string, string>(
                    debuff.Key.Id + "", percentage + ""
                    ));
            }

            foreach (var user in playersInfo.OrderByDescending(x=>x.Amount))
            {
                var teradpsUser = new Members();
                var damage = user.Amount;
                teradpsUser.playerTotalDamage = damage + "";

                if (damage <= 0)
                {
                    continue;
                }

                var buffs = _abnormals.Get(user.Source);
                teradpsUser.playerClass = user.Source.Class.ToString();
                teradpsUser.playerName = user.Source.Name;
                teradpsUser.playerServer = BasicTeraData.Instance.Servers.GetServerName(user.Source.ServerId);
                teradpsUser.playerAverageCritRate = Math.Round(user.CritRate, 1) + "";
                teradpsUser.healCrit = user.Source.IsHealer
                    ? heals.FirstOrDefault(x => x.Source == user.Source)?.CritRate + ""
                    : null;
                teradpsUser.playerDps = TimeSpan.TicksPerSecond*damage/interTick + "";
                teradpsUser.playerTotalDamagePercentage = user.Amount*100/entityInfo.TotalDamage + "";

                extendedStats.PlayerReceived.Add(user.Source.Name, Tuple.Create(skills.HitsReceived(user.Source.User, entity, timedEncounter), skills.DamageReceived(user.Source.User, entity, timedEncounter)));

                var death = buffs.Death;
                teradpsUser.playerDeaths = death.Count(firstTick, lastTick) + "";
                teradpsUser.playerDeathDuration = death.Duration(firstTick, lastTick)/TimeSpan.TicksPerSecond + "";

                var aggro = buffs.Aggro(entity);
                teradpsUser.aggro = 100*aggro.Duration(firstTick, lastTick)/interTick + "";

                foreach (var buff in buffs.Times.OrderByDescending(x=>x.Value.Duration(firstTick, lastTick)))
                {
                    var percentage = buff.Value.Duration(firstTick, lastTick)*100/interTick;
                    if (percentage == 0)
                    {
                        continue;
                    }
                    teradpsUser.buffUptime.Add(new KeyValuePair<string, string>(
                        buff.Key.Id + "", percentage + ""
                        ));
                }
                var serverPlayerName = $"{teradpsUser.playerServer}_{teradpsUser.playerName}";
                extendedStats.PlayerSkills.Add(serverPlayerName,
                    skills.GetSkillsDealt(user.Source.User, entity, timedEncounter));
                extendedStats.PlayerBuffs.Add(serverPlayerName, buffs);

                var skillsId = SkillAggregate.GetAggregate(user, entityInfo.Entity, skills, timedEncounter, Database.Database.Type.Damage);
                extendedStats.PlayerSkillsAggregated[teradpsUser.playerServer + "/" + teradpsUser.playerName] = skillsId;

                foreach (var skill in skillsId.OrderByDescending(x=>x.Amount()))
                {
                    var skillLog = new SkillLog();
                    var skilldamage = skill.Amount();

                    skillLog.skillAverageCrit = Math.Round(skill.AvgCrit()) + "";
                    skillLog.skillAverageWhite = Math.Round(skill.AvgWhite()) + "";
                    skillLog.skillCritRate = skill.CritRate() + "";
                    skillLog.skillDamagePercent = skill.DamagePercent() + "";
                    skillLog.skillHighestCrit = skill.BiggestCrit() + "";
                    skillLog.skillHits = skill.Hits() + "";
                    var skillKey = skill.Skills.First().Key;
                    skillLog.skillId= BasicTeraData.Instance.SkillDatabase.GetSkillByPetName(skillKey.NpcInfo?.Name, user.Source.RaceGenderClass)?.Id.ToString() ?? skillKey.Id.ToString();
                    skillLog.skillLowestCrit = skill.LowestCrit() + "";
                    skillLog.skillTotalDamage = skilldamage + "";

                    if (skilldamage == 0)
                    {
                        continue;
                    }
                    teradpsUser.skillLog.Add(skillLog);
                }
                teradpsData.members.Add(teradpsUser);
            }
            return extendedStats;
        }
コード例 #25
0
        public static Tuple <string, string> Copy(StatsSummary statsSummary, Skills skills, AbnormalityStorage abnormals,
                                                  bool timedEncounter, CopyKey copy)
        {
            //stop if nothing to paste
            var entityInfo   = statsSummary.EntityInformation;
            var playersInfos = statsSummary.PlayerDamageDealt;
            var firstTick    = entityInfo.BeginTime;
            var lastTick     = entityInfo.EndTime;
            var firstHit     = firstTick / TimeSpan.TicksPerSecond;
            var lastHit      = lastTick / TimeSpan.TicksPerSecond;
            var heals        = statsSummary.PlayerHealDealt;

            playersInfos.RemoveAll(x => x.Amount == 0);
            IEnumerable <PlayerDamageDealt> playerInfosOrdered;

            if (copy.Order == "ascending")
            {
                switch (copy.OrderBy)
                {
                case "damage_received":
                    playerInfosOrdered =
                        playersInfos.OrderBy(
                            playerInfo =>
                            skills.DamageReceived(playerInfo.Source.User, entityInfo.Entity,
                                                  timedEncounter));
                    break;

                case "name":
                    playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.Source.Name);
                    break;

                case "damage_percentage":
                case "damage_dealt":
                case "dps":
                    playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.Amount);
                    break;

                case "crit_rate":
                    playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.CritRate);
                    break;

                case "hits_received":
                    playerInfosOrdered =
                        playersInfos.OrderBy(
                            playerInfo =>
                            skills.HitsReceived(playerInfo.Source.User, entityInfo.Entity, timedEncounter));
                    break;

                default:
                    Console.WriteLine("wrong value for orderby");
                    throw new Exception("wrong value for orderby");
                }
            }
            else
            {
                switch (copy.OrderBy)
                {
                case "damage_received":
                    playerInfosOrdered =
                        playersInfos.OrderByDescending(
                            playerInfo =>
                            skills.DamageReceived(playerInfo.Source.User, entityInfo.Entity,
                                                  timedEncounter));
                    break;

                case "name":
                    playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.Source.Name);
                    break;

                case "damage_percentage":
                case "damage_dealt":
                case "dps":
                    playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.Amount);
                    break;

                case "crit_rate":
                    playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.CritRate);
                    break;

                case "hits_received":
                    playerInfosOrdered =
                        playersInfos.OrderByDescending(
                            playerInfo =>
                            skills.HitsReceived(playerInfo.Source.User, entityInfo.Entity, timedEncounter));
                    break;

                default:
                    Console.WriteLine("wrong value for orderby");
                    throw new Exception("wrong value for orderby");
                }
            }

            var dpsString = new StringBuilder(copy.Header + "{body}" + copy.Footer);
            var name      = entityInfo.Entity?.Info.Name ?? "";
            AbnormalityDuration enrage;
            var bossDebuff = abnormals.Get(entityInfo.Entity);

            bossDebuff.TryGetValue(BasicTeraData.Instance.HotDotDatabase.Enraged, out enrage);
            var enrageperc = lastTick - firstTick == 0
                ? 0
                : (double)(enrage?.Duration(firstTick, lastTick) ?? 0) / (lastTick - firstTick);

            dpsString.Replace("{encounter}", name);
            var interval = TimeSpan.FromSeconds(lastHit - firstHit);

            dpsString.Replace("{timer}", interval.ToString(@"mm\:ss"));
            dpsString.Replace("{partyDps}",
                              FormatHelpers.Instance.FormatValue(lastHit - firstHit > 0
                    ? entityInfo.TotalDamage / (lastHit - firstHit)
                    : 0) + LP.PerSecond);
            dpsString.Replace("{enrage}", FormatHelpers.Instance.FormatPercent(enrageperc));
            dpsString.Replace("{debuff_list}", String.Join(" | ",
                                                           bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.Duration(firstTick, lastTick) > 0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick, -1)).ToList().Select(
                                                               x => x.Key.ShortName +
                                                               (x.Value.MaxStack(firstTick, lastTick) > 1 ? "(" + x.Value.MaxStack(firstTick, lastTick) + ")" : "") +
                                                               " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick, -1) / (lastTick - firstTick)) +
                                                               " (" + TimeSpan.FromTicks(x.Value.Duration(firstTick, lastTick, -1)).ToString(@"mm\:ss") + ") ")
                                                           ));
            dpsString.Replace("{debuff_list_p}", String.Join(" | ",
                                                             bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.Duration(firstTick, lastTick) > 0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick, -1)).ToList().Select(
                                                                 x => x.Key.ShortName +
                                                                 (x.Value.MaxStack(firstTick, lastTick) > 1 ? "(" + x.Value.MaxStack(firstTick, lastTick) + ")" : "") +
                                                                 " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick - 1) / (lastTick - firstTick)))
                                                             ));
            var placeholders = new List <KeyValuePair <PlayerDamageDealt, Dictionary <string, string> > >();

            foreach (var playerStats in playerInfosOrdered)
            {
                var playerHolder = new Dictionary <string, string>();
                placeholders.Add(new KeyValuePair <PlayerDamageDealt, Dictionary <string, string> >(playerStats, playerHolder));
                var buffs = abnormals.Get(playerStats.Source);
                AbnormalityDuration slaying;
                var    firstOrDefault = heals.FirstOrDefault(x => x.Source == playerStats.Source);
                double healCritrate   = 0;
                if (firstOrDefault != null)
                {
                    healCritrate = firstOrDefault.CritRate;
                }
                buffs.Times.TryGetValue(BasicTeraData.Instance.HotDotDatabase.Slaying, out slaying);
                var slayingperc = lastTick - firstTick == 0
                    ? 0
                    : (double)(slaying?.Duration(firstTick, lastTick) ?? 0) / (lastTick - firstTick);
                playerHolder["{slaying}"]           = FormatHelpers.Instance.FormatPercent(slayingperc);
                playerHolder["{dps}"]               = FormatHelpers.Instance.FormatValue(playerStats.Interval == 0 ? playerStats.Amount : playerStats.Amount * TimeSpan.TicksPerSecond / playerStats.Interval) + LP.PerSecond;
                playerHolder["{global_dps}"]        = FormatHelpers.Instance.FormatValue(entityInfo.Interval == 0 ? playerStats.Amount : playerStats.Amount * TimeSpan.TicksPerSecond / entityInfo.Interval) + LP.PerSecond;
                playerHolder["{interval}"]          = playerStats.Interval / TimeSpan.TicksPerSecond + LP.Seconds;
                playerHolder["{damage_dealt}"]      = FormatHelpers.Instance.FormatValue(playerStats.Amount);
                playerHolder["{class}"]             = LP.ResourceManager.GetString(playerStats.Source.Class.ToString(), LP.Culture) + "";
                playerHolder["{classId}"]           = ((int)playerStats.Source.Class) + "";
                playerHolder["{fullname}"]          = copy.LimitNameLength > 0 && playerStats.Source.FullName.Length > copy.LimitNameLength ? playerStats.Source.FullName.Substring(0, copy.LimitNameLength) : playerStats.Source.FullName;
                playerHolder["{name}"]              = copy.LimitNameLength > 0 && playerStats.Source.Name.Length > copy.LimitNameLength ? playerStats.Source.Name.Substring(0, copy.LimitNameLength) : playerStats.Source.Name;
                playerHolder["{deaths}"]            = buffs.Death.Count(firstTick, lastTick) + "";
                playerHolder["{death_duration}"]    = TimeSpan.FromTicks(buffs.Death.Duration(firstTick, lastTick)).ToString(@"mm\:ss");
                playerHolder["{aggro}"]             = buffs.Aggro(entityInfo.Entity).Count(firstTick, lastTick) + "";
                playerHolder["{aggro_duration}"]    = TimeSpan.FromTicks(buffs.Aggro(entityInfo.Entity).Duration(firstTick, lastTick)).ToString(@"mm\:ss");
                playerHolder["{damage_percentage}"] = playerStats.Amount * 100 / entityInfo.TotalDamage + "%";
                playerHolder["{crit_rate}"]         = playerStats.CritRate + "%";
                playerHolder["{crit_damage_rate}"]  = playerStats.CritDamageRate + "%";
                playerHolder["{crit_rate_heal}"]    = healCritrate + "%";
                playerHolder["{biggest_crit}"]      = FormatHelpers.Instance.FormatValue(skills.BiggestCrit(playerStats.Source.User, entityInfo.Entity, timedEncounter));
                playerHolder["{damage_received}"]   = FormatHelpers.Instance.FormatValue(skills.DamageReceived(playerStats.Source.User, entityInfo.Entity, timedEncounter));
                playerHolder["{hits_received}"]     = FormatHelpers.Instance.FormatValue(skills.HitsReceived(playerStats.Source.User, entityInfo.Entity, timedEncounter));
                playerHolder["{debuff_list}"]       = String.Join(" | ",
                                                                  bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.InitialPlayerClass == playerStats.Source.Class && x.Value.Duration(firstTick, lastTick) > 0)
                                                                  .OrderByDescending(x => x.Value.Duration(firstTick, lastTick, -1)).ToList().Select(
                                                                      x => x.Key.ShortName +
                                                                      (x.Value.MaxStack(firstTick, lastTick) > 1 ? "(" + x.Value.MaxStack(firstTick, lastTick) + ")" : "") +
                                                                      " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick, -1) / (lastTick - firstTick)) +
                                                                      " (" + TimeSpan.FromTicks(x.Value.Duration(firstTick, lastTick, -1)).ToString(@"mm\:ss") + ") "
                                                                      ));
                playerHolder["{debuff_list_p}"] = String.Join(" | ",
                                                              bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.InitialPlayerClass == playerStats.Source.Class && x.Value.Duration(firstTick, lastTick) > 0)
                                                              .OrderByDescending(x => x.Value.Duration(firstTick, lastTick, -1)).ToList().Select(
                                                                  x => x.Key.ShortName +
                                                                  (x.Value.MaxStack(firstTick, lastTick) > 1 ? "(" + x.Value.MaxStack(firstTick, lastTick) + ")" : "") +
                                                                  " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick, -1) / (lastTick - firstTick))
                                                                  ));
            }
            var placeholderLength = placeholders.SelectMany(x => x.Value).GroupBy(x => x.Key).ToDictionary(x => x.Key, x => x.Max(z => graphics.MeasureString(z.Value, Font, default(PointF), StringFormat.GenericTypographic).Width));
            var dpsLine           = new StringBuilder();
            var dpsMono           = new StringBuilder();
            var placeholderMono   = placeholders.SelectMany(x => x.Value).GroupBy(x => x.Key).ToDictionary(x => x.Key, x => x.Max(z => z.Value.Length));

            if ((copy.Content.Contains('\\') || copy.LowDpsContent.Contains('\\')) && BasicTeraData.Instance.WindowData.FormatPasteString)
            {
                placeholders.ForEach(x =>
                {
                    var currentContent = x.Key.Amount * 100 / entityInfo.TotalDamage >= copy.LowDpsThreshold ? new StringBuilder(copy.Content): new StringBuilder(copy.LowDpsContent);
                    x.Value.ToList().ForEach(z => currentContent.Replace(z.Key, PadRight(z.Value, placeholderLength[z.Key])));
                    dpsLine.Append(currentContent);
                    currentContent = x.Key.Amount * 100 / entityInfo.TotalDamage >= copy.LowDpsThreshold ? new StringBuilder(copy.Content) : new StringBuilder(copy.LowDpsContent);
                    x.Value.ToList().ForEach(z => currentContent.Replace(z.Key, z.Value.PadRight(placeholderMono[z.Key])));
                    dpsMono.Append(currentContent);
                });
            }
            else
            {
                placeholders.ForEach(x =>
                {
                    var currentContent = x.Key.Amount * 100 / entityInfo.TotalDamage >= copy.LowDpsThreshold ? new StringBuilder(copy.Content) : new StringBuilder(copy.LowDpsContent);
                    x.Value.ToList().ForEach(z => currentContent.Replace(z.Key, z.Value));
                    dpsLine.Append(currentContent);
                });
                dpsMono = dpsLine;
            }
            var paste     = dpsString.ToString().Replace("{body}", dpsLine.ToString());
            var monoPaste = dpsString.ToString().Replace("{body}", dpsMono.ToString());

            while (paste.Contains(" )"))
            {
                paste = paste.Replace(" )", ") ");
            }
            while (monoPaste.Contains(" )"))
            {
                monoPaste = monoPaste.Replace(" )", ") ");
            }
            while (paste.Contains(" ]"))
            {
                paste = paste.Replace(" ]", "] ");
            }
            while (monoPaste.Contains(" ]"))
            {
                monoPaste = monoPaste.Replace(" ]", "] ");
            }
            while (paste.Contains(" \\"))
            {
                paste = paste.Replace(" \\", "\\");
            }
            while (monoPaste.Contains(" \\"))
            {
                monoPaste = monoPaste.Replace(" \\", "\\");
            }
            monoPaste = monoPaste.Replace("\\", Environment.NewLine);
            return(new Tuple <string, string>(paste, monoPaste));
        }
コード例 #26
0
        public static string Copy(EntityInfo info, IEnumerable <PlayerInfo> playerInfos, AbnormalityStorage abnormals, long totalDamage, long partyDps, long firstHit, long lastHit, Entity currentBoss, bool timedEncounter, string header,
                                  string content, string footer,
                                  string orderby, string order)
        {
            //stop if nothing to paste
            if (playerInfos == null)
            {
                return("");
            }
            IEnumerable <PlayerInfo> playerInfosOrdered;

            if (order == "ascending")
            {
                switch (orderby)
                {
                case "damage_received":
                    playerInfosOrdered = playerInfos.OrderBy(playerInfo => playerInfo.Received.Damage(currentBoss, firstHit, lastHit, timedEncounter));
                    break;

                case "name":
                    playerInfosOrdered = playerInfos.OrderBy(playerInfo => playerInfo.Name);
                    break;

                case "damage_percentage":
                    playerInfosOrdered =
                        playerInfos.OrderBy(playerInfo => playerInfo.Dealt.DamageFraction(currentBoss, totalDamage, timedEncounter));
                    break;

                case "damage_dealt":
                    playerInfosOrdered = playerInfos.OrderBy(playerInfo => playerInfo.Dealt.Damage(currentBoss, timedEncounter));
                    break;

                case "dps":
                    playerInfosOrdered = playerInfos.OrderBy(playerInfo => playerInfo.Dealt.Dps(currentBoss, timedEncounter));
                    break;

                case "crit_rate":
                    playerInfosOrdered = playerInfos.OrderBy(playerInfo => playerInfo.Dealt.CritRate(currentBoss, timedEncounter));
                    break;

                case "hits_received":
                    playerInfosOrdered =
                        playerInfos.OrderBy(playerInfo => playerInfo.Received.Hits(currentBoss, firstHit, lastHit, timedEncounter));
                    break;

                default:
                    Console.WriteLine("wrong value for orderby");
                    throw new Exception("wrong value for orderby");
                }
            }
            else
            {
                switch (orderby)
                {
                case "damage_received":
                    playerInfosOrdered =
                        playerInfos.OrderByDescending(playerInfo => playerInfo.Received.Damage(currentBoss, firstHit, lastHit, timedEncounter));
                    break;

                case "hits_received":
                    playerInfosOrdered =
                        playerInfos.OrderByDescending(playerInfo => playerInfo.Received.Hits(currentBoss, firstHit, lastHit, timedEncounter));
                    break;

                case "name":
                    playerInfosOrdered = playerInfos.OrderByDescending(playerInfo => playerInfo.Name);
                    break;

                case "damage_percentage":
                    playerInfosOrdered =
                        playerInfos.OrderByDescending(playerInfo => playerInfo.Dealt.DamageFraction(currentBoss, totalDamage, timedEncounter));
                    break;

                case "damage_dealt":
                    playerInfosOrdered =
                        playerInfos.OrderByDescending(playerInfo => playerInfo.Dealt.Damage(currentBoss, timedEncounter));
                    break;

                case "dps":
                    playerInfosOrdered = playerInfos.OrderByDescending(playerInfo => playerInfo.Dealt.Dps(currentBoss, timedEncounter));
                    break;

                case "crit_rate":
                    playerInfosOrdered =
                        playerInfos.OrderByDescending(playerInfo => playerInfo.Dealt.CritRate(currentBoss, timedEncounter));
                    break;

                default:
                    Console.WriteLine("wrong value for orderby");
                    throw new Exception("wrong value for orderby");
                }
            }

            var    dpsString  = header;
            var    name       = "";
            double enrageperc = 0;

            if (currentBoss != null)
            {
                name = currentBoss.Name;
                AbnormalityDuration enrage;
                abnormals.Get(currentBoss.NpcE).TryGetValue(BasicTeraData.Instance.HotDotDatabase.Get(8888888), out enrage);
                enrageperc = (lastHit - firstHit) == 0 ? 0 : (((double)(enrage?.Duration(firstHit, lastHit) ?? 0) / (lastHit - firstHit)));
            }

            dpsString = dpsString.Replace("{encounter}", name);
            var interval = TimeSpan.FromSeconds(lastHit - firstHit);

            dpsString = dpsString.Replace("{timer}", interval.ToString(@"mm\:ss"));
            dpsString = dpsString.Replace("{partyDps}", FormatHelpers.Instance.FormatValue(partyDps) + "/s");
            dpsString = dpsString.Replace("{enrage}", FormatHelpers.Instance.FormatPercent(enrageperc));

            foreach (var playerStats in playerInfosOrdered)
            {
                var currentContent = content;
                if (playerStats.Dealt.Damage(currentBoss, timedEncounter) == 0)
                {
                    continue;
                }

                var buffs = abnormals.Get(playerStats.Player);
                AbnormalityDuration slaying;
                buffs.Times.TryGetValue(BasicTeraData.Instance.HotDotDatabase.Get(8888889), out slaying);
                double slayingperc = (lastHit - firstHit) == 0 ? 0 : (((double)(slaying?.Duration(firstHit, lastHit) ?? 0) / (lastHit - firstHit)));
                currentContent = currentContent.Replace("{slaying}", FormatHelpers.Instance.FormatPercent(slayingperc));
                currentContent = currentContent.Replace("{dps}",
                                                        FormatHelpers.Instance.FormatValue(playerStats.Dealt.Dps(currentBoss, timedEncounter)) + "/s");
                currentContent = currentContent.Replace("{global_dps}",
                                                        FormatHelpers.Instance.FormatValue(playerStats.Dealt.GlobalDps(currentBoss, timedEncounter, lastHit - firstHit)) + "/s");
                currentContent = currentContent.Replace("{interval}", playerStats.Dealt.Interval(currentBoss) + "s");
                currentContent = currentContent.Replace("{damage_dealt}",
                                                        FormatHelpers.Instance.FormatValue(playerStats.Dealt.Damage(currentBoss, timedEncounter)));
                currentContent = currentContent.Replace("{class}", playerStats.Class + "");
                currentContent = currentContent.Replace("{fullname}", playerStats.Player.FullName);
                currentContent = currentContent.Replace("{name}", playerStats.Name);
                currentContent = currentContent.Replace("{deaths}", buffs.Death.Count(firstHit, lastHit) + "");
                currentContent = currentContent.Replace("{death_duration}", TimeSpan.FromSeconds(buffs.Death.Duration(firstHit, lastHit)).ToString(@"mm\:ss"));
                currentContent = currentContent.Replace("{aggro}", buffs.Aggro(currentBoss?.NpcE).Count(firstHit, lastHit) + "");
                currentContent = currentContent.Replace("{aggro_duration}", TimeSpan.FromSeconds(buffs.Aggro(currentBoss?.NpcE).Duration(firstHit, lastHit)).ToString(@"mm\:ss"));
                currentContent = currentContent.Replace("{damage_percentage}",
                                                        playerStats.Dealt.DamageFraction(currentBoss, totalDamage, timedEncounter) + "%");
                currentContent = currentContent.Replace("{crit_rate}", playerStats.Dealt.CritRate(currentBoss, timedEncounter) + "%");
                currentContent = currentContent.Replace("{biggest_crit}", FormatHelpers.Instance.FormatValue(playerStats.Dealt.DmgBiggestCrit(currentBoss, timedEncounter)));
                currentContent = currentContent.Replace("{damage_received}",
                                                        FormatHelpers.Instance.FormatValue(playerStats.Received.Damage(currentBoss, firstHit, lastHit, timedEncounter)));
                currentContent = currentContent.Replace("{hits_received}",
                                                        FormatHelpers.Instance.FormatValue(playerStats.Received.Hits(currentBoss, firstHit, lastHit, timedEncounter)));

                dpsString += currentContent;
            }
            dpsString += footer;
            return(dpsString);
        }
コード例 #27
0
        public void Update(StatsSummary nstatsSummary, Database.Structures.Skills nskills, List <NpcEntity> nentities, bool ntimedEncounter,
                           AbnormalityStorage nabnormals, ConcurrentDictionary <string, NpcEntity> nbossHistory, List <ChatMessage> nchatbox, int npacketWaiting,
                           NotifyFlashMessage nflash)
        {
            void ChangeUi(StatsSummary statsSummary, Database.Structures.Skills skills, List <NpcEntity> entities, bool timedEncounter, AbnormalityStorage abnormals,
                          ConcurrentDictionary <string, NpcEntity> bossHistory, List <ChatMessage> chatbox, int packetWaiting, NotifyFlashMessage flash)
            {
                Scroller.MaxHeight = BasicTeraData.Instance.WindowData.NumberOfPlayersDisplayed * 30;
                UpdateComboboxEncounter(entities, statsSummary.EntityInformation.Entity);
                _entityStats.Update(statsSummary.EntityInformation, abnormals);
                _windowHistory.Update(bossHistory);
                _chatbox?.Update(chatbox);

                NotifyIcon.ShowBallon(flash);
                NotifyIcon.UpdatePacketWaiting(packetWaiting);

                PartyDps.Content = FormatHelpers.Instance.FormatValue(statsSummary.EntityInformation.Interval == 0
                                       ? statsSummary.EntityInformation.TotalDamage
                                       : statsSummary.EntityInformation.TotalDamage * TimeSpan.TicksPerSecond / statsSummary.EntityInformation.Interval) +
                                   LP.PerSecond;
                var visiblePlayerStats = new HashSet <Player>();
                var statsDamage        = statsSummary.PlayerDamageDealt;
                var statsHeal          = statsSummary.PlayerHealDealt;

                foreach (var playerStats in statsDamage)
                {
                    PlayerStats playerStatsControl;
                    Controls.TryGetValue(playerStats.Source, out playerStatsControl);
                    if (playerStats.Amount == 0)
                    {
                        continue;
                    }

                    visiblePlayerStats.Add(playerStats.Source);
                    if (playerStatsControl != null)
                    {
                        continue;
                    }
                    playerStatsControl = new PlayerStats(playerStats, statsHeal.FirstOrDefault(x => x.Source == playerStats.Source), statsSummary.EntityInformation,
                                                         skills, abnormals.Get(playerStats.Source));
                    Controls.Add(playerStats.Source, playerStatsControl);
                }

                var invisibleControls = Controls.Where(x => !visiblePlayerStats.Contains(x.Key)).ToList();

                foreach (var invisibleControl in invisibleControls)
                {
                    Controls[invisibleControl.Key].CloseSkills();
                    Controls.Remove(invisibleControl.Key);
                }

                TotalDamage.Content = FormatHelpers.Instance.FormatValue(statsSummary.EntityInformation.TotalDamage);
                if (BasicTeraData.Instance.WindowData.ShowTimeLeft && statsSummary.EntityInformation.TimeLeft > 0)
                {
                    var interval = TimeSpan.FromSeconds(statsSummary.EntityInformation.TimeLeft / TimeSpan.TicksPerSecond);
                    Timer.Content    = interval.ToString(@"mm\:ss");
                    Timer.Foreground = Brushes.LightCoral;
                }
                else
                {
                    var interval = TimeSpan.FromSeconds(statsSummary.EntityInformation.Interval / TimeSpan.TicksPerSecond);
                    Timer.Content = interval.ToString(@"mm\:ss");
                    if (statsSummary.EntityInformation.Interval == 0 && BasicTeraData.Instance.WindowData.ShowTimeLeft)
                    {
                        Timer.Foreground = Brushes.LightCoral;
                    }
                    else
                    {
                        Timer.Foreground = Brushes.White;
                    }
                }
                Players.Items.Clear();

                foreach (var item in statsDamage)
                {
                    if (!Controls.ContainsKey(item.Source))
                    {
                        continue;
                    }
                    if (Players.Items.Contains(Controls[item.Source]))
                    {
                        BasicTeraData.LogError(
                            "duplicate playerinfo: \r\n" + string.Join("\r\n ", statsDamage.Select(x => x.Source.ToString() + " ->  " + x.Amount)), false, true);
                        continue;
                    }
                    Players.Items.Add(Controls[item.Source]);
                    Controls[item.Source].Repaint(item, statsHeal.FirstOrDefault(x => x.Source == item.Source), statsSummary.EntityInformation, skills,
                                                  abnormals.Get(item.Source), timedEncounter);
                }

                if (BasicTeraData.Instance.WindowData.InvisibleUi)
                {
                    if (Controls.Count > 0 && !ForceWindowVisibilityHidden)
                    {
                        Visibility = Visibility.Visible;
                    }
                    if (Controls.Count == 0)
                    {
                        Visibility = Visibility.Hidden;
                    }
                }
                else
                {
                    if (!ForceWindowVisibilityHidden)
                    {
                        Visibility = Visibility.Visible;
                    }
                }
                if (ActualWidth != _oldWidth) // auto snap to right screen border on width change
                {
                    var screen = Screen.FromHandle(new WindowInteropHelper(GetWindow(this)).Handle);
                    // Transform screen point to WPF device independent point
                    var source = PresentationSource.FromVisual(this);
                    if (source?.CompositionTarget == null)
                    {
                        return;
                    }
                    var dx = source.CompositionTarget.TransformToDevice.M11;
                    if (Math.Abs(screen.WorkingArea.X + screen.WorkingArea.Width - (Left + _oldWidth) * dx) < 50) //snap at 50 px
                    {
                        Left = Left + _oldWidth - ActualWidth;
                    }
                    _oldWidth = ActualWidth;
                }
            }

            Dispatcher.Invoke((NetworkController.UpdateUiHandler)ChangeUi, nstatsSummary, nskills, nentities, ntimedEncounter, nabnormals, nbossHistory, nchatbox,
                              npacketWaiting, nflash);
        }
コード例 #28
0
        private void PacketAnalysisLoop()
        {
            try { Database.Database.Instance.DeleteAll(); }
            catch (Exception ex)
            {
                BasicTeraData.LogError(
                    ex.Message + "\r\n" + ex.StackTrace + "\r\n" + ex.Source + "\r\n" + ex + "\r\n" + ex.Data + "\r\n" + ex.InnerException + "\r\n" + ex.TargetSite,
                    true);
                MessageBox.Show(LP.MainWindow_Fatal_error);
                Exit();
            }

            while (_keepAlive)
            {
                if (NeedToCopy != null)
                {
                    var currentBoss    = Encounter;
                    var timedEncounter = TimedEncounter;

                    var entityInfo  = Database.Database.Instance.GlobalInformationEntity(currentBoss, timedEncounter);
                    var skills      = Database.Database.Instance.GetSkills(entityInfo.BeginTime, entityInfo.EndTime);
                    var playersInfo = timedEncounter
                        ? Database.Database.Instance.PlayerDamageInformation(entityInfo.BeginTime, entityInfo.EndTime)
                        : Database.Database.Instance.PlayerDamageInformation(currentBoss);
                    var heals        = Database.Database.Instance.PlayerHealInformation(entityInfo.BeginTime, entityInfo.EndTime);
                    var statsSummary = new StatsSummary(playersInfo, heals, entityInfo);

                    var tmpcopy     = NeedToCopy;
                    var abnormals   = AbnormalityStorage.Clone(currentBoss, entityInfo.BeginTime, entityInfo.EndTime);
                    var pasteThread = new Thread(() => CopyThread(statsSummary, skills, abnormals, timedEncounter, tmpcopy))
                    {
                        Priority = ThreadPriority.Highest
                    };
                    pasteThread.SetApartmentState(ApartmentState.STA);
                    pasteThread.Start();

                    NeedToCopy = null;
                }

                if (NeedToReset)
                {
                    Reset();
                    NeedToReset = false;
                }

                if (NeedToResetCurrent)
                {
                    ResetCurrent();
                    NeedToResetCurrent = false;
                }

                if (!NeedToExport.HasFlag(DataExporter.Dest.None))
                {
                    DataExporter.ManualExport(Encounter, AbnormalityStorage, NeedToExport);
                    NeedToExport = DataExporter.Dest.None;
                }

                Encounter = NewEncounter;

                var packetsWaiting = TeraSniffer.Instance.Packets.Count;
                if (packetsWaiting > 5000)
                {
                    PacketProcessing.Pause();
                    Database.Database.Instance.DeleteAll();
                    AbnormalityStorage = new AbnormalityStorage();
                    AbnormalityTracker = new AbnormalityTracker(EntityTracker, PlayerTracker, BasicTeraData.Instance.HotDotDatabase, AbnormalityStorage, DamageTracker.Instance.Update);
                    HudManager.Instance.CurrentBosses.DisposeAll();
                    TeraSniffer.Instance.Packets = new ConcurrentQueue <Message>();
                    NotifyProcessor.Instance.S_LOAD_TOPO(null);
                    RaisePause(true);
                }

                if (_forceUiUpdate)
                {
                    UpdateUi(packetsWaiting);
                    _forceUiUpdate = false;
                }

                CheckUpdateUi(packetsWaiting);

                Message obj;
                var     successDequeue = TeraSniffer.Instance.Packets.TryDequeue(out obj);
                if (!successDequeue)
                {
                    Thread.Sleep(1);
                    continue;
                }

                var message = MessageFactory.Create(obj);
                if (message.GetType() == typeof(UnknownMessage))
                {
                    continue;
                }

                if (!PacketProcessing.Process(message))
                {
                    //Unprocessed packet
                }
            }
        }
コード例 #29
0
        public static void CopyThread(EntityInfo info, List <PlayerInfo> stats, AbnormalityStorage abnormals, long total, long partyDps, long firstHit, long lastHit, Entity currentBoss, bool timedEncounter, CopyKey copy)
        {
            var text = CopyPaste.Copy(info, stats, abnormals, total, partyDps, firstHit, lastHit, currentBoss, timedEncounter, copy.Header, copy.Content, copy.Footer, copy.OrderBy, copy.Order);

            CopyPaste.Paste(text);
        }
コード例 #30
0
 public static void CopyThread(StatsSummary stats, Skills skills, AbnormalityStorage abnormals,
     bool timedEncounter, CopyKey copy)
 {
     if (BasicTeraData.Instance.HotDotDatabase == null) return;//no database loaded yet => no need to do anything
     lock (pasteLock)
     {
         var text = CopyPaste.Copy(stats, skills, abnormals, timedEncounter, copy.Header, copy.Content,
             copy.Footer,
             copy.OrderBy, copy.Order,copy.LowDpsContent,copy.LowDpsThreshold);
         for (var i = 0; i < 3; i++)
         {
             try
             {
                 Clipboard.SetText(text.Item2);
                 break;
             }
             catch
             {
                 Thread.Sleep(100);
                 //Ignore
             }
         }
         CopyPaste.Paste(text.Item1);
     }
 }
コード例 #31
0
ファイル: DataExporter.cs プロジェクト: stas2130/ShinraMeter
        private static ExtendedStats GenerateStats(NpcEntity entity, AbnormalityStorage abnormals)
        {
            if (!entity.Info.Boss)
            {
                return(null);
            }

            var timedEncounter = false;

            /*
             * modify timedEncounter depending on teradps.io need
             *
             */

            var entityInfo  = Database.Database.Instance.GlobalInformationEntity(entity, timedEncounter);
            var skills      = Database.Database.Instance.GetSkills(entityInfo.BeginTime, entityInfo.EndTime);
            var playersInfo = timedEncounter
                ? Database.Database.Instance.PlayerDamageInformation(entityInfo.BeginTime, entityInfo.EndTime)
                : Database.Database.Instance.PlayerDamageInformation(entity);
            var heals = Database.Database.Instance.PlayerHealInformation(entityInfo.BeginTime, entityInfo.EndTime);

            playersInfo.RemoveAll(x => x.Amount == 0);

            var firstTick = entityInfo.BeginTime;
            var lastTick  = entityInfo.EndTime;
            var interTick = lastTick - firstTick;
            var interval  = interTick / TimeSpan.TicksPerSecond;

            if (interval == 0)
            {
                return(null);
            }
            var totaldamage = entityInfo.TotalDamage;
            var partyDps    = TimeSpan.TicksPerSecond * totaldamage / interTick;

            var teradpsData   = new EncounterBase();
            var extendedStats = new ExtendedStats();
            var _abnormals    = abnormals.Clone(entity, firstTick, lastTick);

            extendedStats.Entity      = entity;
            extendedStats.BaseStats   = teradpsData;
            extendedStats.FirstTick   = firstTick;
            extendedStats.LastTick    = lastTick;
            teradpsData.areaId        = entity.Info.HuntingZoneId + "";
            teradpsData.bossId        = entity.Info.TemplateId + "";
            teradpsData.fightDuration = interval + "";
            teradpsData.partyDps      = partyDps + "";
            extendedStats.Debuffs     = _abnormals.Get(entity);

            foreach (var debuff in extendedStats.Debuffs)
            {
                var percentage = debuff.Value.Duration(firstTick, lastTick) * 100 / interTick;
                if (percentage == 0)
                {
                    continue;
                }
                teradpsData.debuffUptime.Add(new KeyValuePair <string, string>(
                                                 debuff.Key.Id + "", percentage + ""
                                                 ));
            }

            foreach (var user in playersInfo)
            {
                var teradpsUser = new Members();
                var damage      = user.Amount;
                teradpsUser.playerTotalDamage = damage + "";

                if (damage <= 0)
                {
                    continue;
                }

                var buffs = _abnormals.Get(user.Source);
                teradpsUser.playerClass           = user.Source.Class.ToString();
                teradpsUser.playerName            = user.Source.Name;
                teradpsUser.playerServer          = BasicTeraData.Instance.Servers.GetServerName(user.Source.ServerId);
                teradpsUser.playerAverageCritRate = Math.Round(user.CritRate, 1) + "";
                teradpsUser.healCrit = user.Source.IsHealer
                    ? heals.FirstOrDefault(x => x.Source == user.Source)?.CritRate + ""
                    : null;
                teradpsUser.playerDps = TimeSpan.TicksPerSecond * damage / interTick + "";
                teradpsUser.playerTotalDamagePercentage = user.Amount * 100 / entityInfo.TotalDamage + "";

                extendedStats.PlayerReceived.Add(user.Source.Name, Tuple.Create(skills.HitsReceived(user.Source.User.Id, entity, timedEncounter), skills.DamageReceived(user.Source.User.Id, entity, timedEncounter)));

                var death = buffs.Death;
                teradpsUser.playerDeaths        = death.Count(firstTick, lastTick) + "";
                teradpsUser.playerDeathDuration = death.Duration(firstTick, lastTick) / TimeSpan.TicksPerSecond + "";

                var aggro = buffs.Aggro(entity);
                teradpsUser.aggro = 100 * aggro.Duration(firstTick, lastTick) / interTick + "";

                foreach (var buff in buffs.Times)
                {
                    var percentage = buff.Value.Duration(firstTick, lastTick) * 100 / interTick;
                    if (percentage == 0)
                    {
                        continue;
                    }
                    teradpsUser.buffUptime.Add(new KeyValuePair <string, string>(
                                                   buff.Key.Id + "", percentage + ""
                                                   ));
                }
                var serverPlayerName = $"{teradpsUser.playerServer}_{teradpsUser.playerName}";
                extendedStats.PlayerSkills.Add(serverPlayerName,
                                               skills.GetSkillsDealt(user.Source.User.Id, entity, timedEncounter));
                extendedStats.PlayerBuffs.Add(serverPlayerName, buffs);

                var skillsId = SkillAggregate.GetAggregate(user, entityInfo.Entity, skills, timedEncounter, Database.Database.Type.Damage);
                extendedStats.PlayerSkillsAggregated[teradpsUser.playerServer + "/" + teradpsUser.playerName] = skillsId;

                foreach (var skill in skillsId)
                {
                    var skillLog    = new SkillLog();
                    var skilldamage = skill.Amount();

                    skillLog.skillAverageCrit   = Math.Round(skill.AvgCrit()) + "";
                    skillLog.skillAverageWhite  = Math.Round(skill.AvgWhite()) + "";
                    skillLog.skillCritRate      = skill.CritRate() + "";
                    skillLog.skillDamagePercent = skill.DamagePercent() + "";
                    skillLog.skillHighestCrit   = skill.BiggestCrit() + "";
                    skillLog.skillHits          = skill.Hits() + "";
                    skillLog.skillId            = skill.Skills.First().Key.Id + "";
                    skillLog.skillLowestCrit    = skill.LowestCrit() + "";
                    skillLog.skillTotalDamage   = skilldamage + "";


                    if (skilldamage == 0)
                    {
                        continue;
                    }
                    teradpsUser.skillLog.Add(skillLog);
                }
                teradpsData.members.Add(teradpsUser);
            }
            return(extendedStats);
        }
コード例 #32
0
ファイル: CopyPaste.cs プロジェクト: neowutran/ShinraMeter
        public static Tuple<string, string> Copy(StatsSummary statsSummary, Skills skills, AbnormalityStorage abnormals,
            bool timedEncounter, string header, string content,
            string footer, string orderby, string order, string lowDpsContent, int lowDpsThreshold)
        {
            //stop if nothing to paste
            var entityInfo = statsSummary.EntityInformation;
            var playersInfos = statsSummary.PlayerDamageDealt;
            var firstTick = entityInfo.BeginTime;
            var lastTick = entityInfo.EndTime;
            var firstHit = firstTick/TimeSpan.TicksPerSecond;
            var lastHit = lastTick/TimeSpan.TicksPerSecond;
            var heals = statsSummary.PlayerHealDealt;
            playersInfos.RemoveAll(x => x.Amount == 0);

            IEnumerable<PlayerDamageDealt> playerInfosOrdered;
            if (order == "ascending")
            {
                switch (orderby)
                {
                    case "damage_received":
                        playerInfosOrdered =
                            playersInfos.OrderBy(
                                playerInfo =>
                                    skills.DamageReceived(playerInfo.Source.User, entityInfo.Entity,
                                        timedEncounter));
                        break;
                    case "name":
                        playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.Source.Name);
                        break;
                    case "damage_percentage":
                    case "damage_dealt":
                    case "dps":
                        playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.Amount);
                        break;
                    case "crit_rate":
                        playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.CritRate);
                        break;
                    case "hits_received":
                        playerInfosOrdered =
                            playersInfos.OrderBy(
                                playerInfo =>
                                    skills.HitsReceived(playerInfo.Source.User, entityInfo.Entity, timedEncounter));
                        break;
                    default:
                        Console.WriteLine("wrong value for orderby");
                        throw new Exception("wrong value for orderby");
                }
            }
            else
            {
                switch (orderby)
                {
                    case "damage_received":
                        playerInfosOrdered =
                            playersInfos.OrderByDescending(
                                playerInfo =>
                                    skills.DamageReceived(playerInfo.Source.User, entityInfo.Entity,
                                        timedEncounter));
                        break;
                    case "name":
                        playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.Source.Name);
                        break;
                    case "damage_percentage":
                    case "damage_dealt":
                    case "dps":
                        playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.Amount);
                        break;
                    case "crit_rate":
                        playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.CritRate);
                        break;
                    case "hits_received":
                        playerInfosOrdered =
                            playersInfos.OrderByDescending(
                                playerInfo =>
                                    skills.HitsReceived(playerInfo.Source.User, entityInfo.Entity, timedEncounter));
                        break;
                    default:
                        Console.WriteLine("wrong value for orderby");
                        throw new Exception("wrong value for orderby");
                }
            }

            var dpsString = new StringBuilder(header);

            var name = entityInfo.Entity?.Info.Name ?? "";
            AbnormalityDuration enrage;
            var bossDebuff = abnormals.Get(entityInfo.Entity);
            bossDebuff.TryGetValue(BasicTeraData.Instance.HotDotDatabase.Enraged, out enrage);
            var enrageperc = lastTick - firstTick == 0
                ? 0
                : (double) (enrage?.Duration(firstTick, lastTick) ?? 0)/(lastTick - firstTick);

            dpsString.Replace("{encounter}", name);
            var interval = TimeSpan.FromSeconds(lastHit - firstHit);
            dpsString.Replace("{timer}", interval.ToString(@"mm\:ss"));
            dpsString.Replace("{partyDps}",
                FormatHelpers.Instance.FormatValue(lastHit - firstHit > 0
                    ? entityInfo.TotalDamage/(lastHit - firstHit)
                    : 0) + LP.PerSecond);
            dpsString.Replace("{enrage}", FormatHelpers.Instance.FormatPercent(enrageperc));
            dpsString.Replace("{debuff_list}", String.Join(" | ",
                bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.Duration(firstTick, lastTick) > 0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick)).ToList().Select(
                    x => x.Key.ShortName + " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick) / (lastTick - firstTick)) +
                        " (" + TimeSpan.FromTicks(x.Value.Duration(firstTick, lastTick)).ToString(@"mm\:ss") + ") ")
            ));
            dpsString.Replace("{debuff_list_p}", String.Join(" | ",
                bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.Duration(firstTick, lastTick) > 0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick)).ToList().Select(
                    x => x.Key.ShortName + " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick) / (lastTick - firstTick)))
            ));

            var placeholders = new List<KeyValuePair<PlayerDamageDealt, Dictionary<string, string>>>();
            foreach (var playerStats in playerInfosOrdered)
            {
                var playerHolder = new Dictionary<string, string>();
                placeholders.Add(new KeyValuePair<PlayerDamageDealt, Dictionary<string, string>>(playerStats, playerHolder));
                var buffs = abnormals.Get(playerStats.Source);
                AbnormalityDuration slaying;
                var firstOrDefault = heals.FirstOrDefault(x => x.Source == playerStats.Source);
                double healCritrate = 0;
                if (firstOrDefault != null)
                {
                    healCritrate = firstOrDefault.CritRate;
                }
                buffs.Times.TryGetValue(BasicTeraData.Instance.HotDotDatabase.Slaying, out slaying);
                var slayingperc = lastTick - firstTick == 0
                    ? 0
                    : (double)(slaying?.Duration(firstTick, lastTick) ?? 0) / (lastTick - firstTick);
                playerHolder["{slaying}"] = FormatHelpers.Instance.FormatPercent(slayingperc);
                playerHolder["{dps}"] = FormatHelpers.Instance.FormatValue(playerStats.Interval == 0 ? playerStats.Amount : playerStats.Amount * TimeSpan.TicksPerSecond / playerStats.Interval) + LP.PerSecond;
                playerHolder["{global_dps}"] = FormatHelpers.Instance.FormatValue(entityInfo.Interval == 0 ? playerStats.Amount : playerStats.Amount * TimeSpan.TicksPerSecond / entityInfo.Interval) + LP.PerSecond;
                playerHolder["{interval}"] = playerStats.Interval/TimeSpan.TicksPerSecond + LP.Seconds;
                playerHolder["{damage_dealt}"] = FormatHelpers.Instance.FormatValue(playerStats.Amount);
                playerHolder["{class}"] = LP.ResourceManager.GetString(playerStats.Source.Class.ToString(), LP.Culture) + "";
                playerHolder["{fullname}"] = playerStats.Source.FullName;
                playerHolder["{name}"] = playerStats.Source.Name;
                playerHolder["{deaths}"] = buffs.Death.Count(firstTick, lastTick) + "";
                playerHolder["{death_duration}"] = TimeSpan.FromTicks(buffs.Death.Duration(firstTick, lastTick)).ToString(@"mm\:ss");
                playerHolder["{aggro}"] = buffs.Aggro(entityInfo.Entity).Count(firstTick, lastTick) + "";
                playerHolder["{aggro_duration}"] = TimeSpan.FromTicks(buffs.Aggro(entityInfo.Entity).Duration(firstTick, lastTick)).ToString(@"mm\:ss");
                playerHolder["{damage_percentage}"] = playerStats.Amount * 100 / entityInfo.TotalDamage + "%";
                playerHolder["{crit_rate}"] = playerStats.CritRate + "%";
                playerHolder["{crit_rate_heal}"] = healCritrate + "%";
                playerHolder["{biggest_crit}"] = FormatHelpers.Instance.FormatValue(skills.BiggestCrit(playerStats.Source.User, entityInfo.Entity, timedEncounter));
                playerHolder["{damage_received}"] = FormatHelpers.Instance.FormatValue(skills.DamageReceived(playerStats.Source.User, entityInfo.Entity, timedEncounter));
                playerHolder["{hits_received}"] = FormatHelpers.Instance.FormatValue(skills.HitsReceived(playerStats.Source.User, entityInfo.Entity, timedEncounter));
                playerHolder["{debuff_list}"] = String.Join(" | ",
                    bossDebuff.Where(x=>x.Key.Id!=8888888 && x.Value.InitialPlayerClass==playerStats.Source.Class && x.Value.Duration(firstTick,lastTick)>0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick)).ToList().Select(
                        x=>x.Key.ShortName + " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick,lastTick) / (lastTick - firstTick)) +
                            " ("+ TimeSpan.FromTicks(x.Value.Duration(firstTick, lastTick)).ToString(@"mm\:ss")+") ")
                );
                playerHolder["{debuff_list_p}"] = String.Join(" | ",
                    bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.InitialPlayerClass == playerStats.Source.Class && x.Value.Duration(firstTick, lastTick) > 0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick)).ToList().Select(
                        x => x.Key.ShortName + " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick) / (lastTick - firstTick)))
                );
            }
            var placeholderLength = placeholders.SelectMany(x => x.Value).GroupBy(x=>x.Key).ToDictionary(x=>x.Key,x=>x.Max(z=> graphics.MeasureString(z.Value, Font, default(PointF), StringFormat.GenericTypographic).Width));
            var dpsmono = new StringBuilder(dpsString.ToString());
            var placeholderMono = placeholders.SelectMany(x => x.Value).GroupBy(x => x.Key).ToDictionary(x => x.Key, x => x.Max(z => z.Value.Length));
            if ((content.Contains('\\')||lowDpsContent.Contains('\\')) && BasicTeraData.Instance.WindowData.FormatPasteString)
                placeholders.ForEach(x =>
                {
                    var currentContent = x.Key.Amount*100/entityInfo.TotalDamage >= lowDpsThreshold ? new StringBuilder(content): new StringBuilder(lowDpsContent);
                    x.Value.ToList().ForEach(z => currentContent.Replace(z.Key, PadRight(z.Value,placeholderLength[z.Key])));
                    dpsString.Append(currentContent);
                    currentContent = x.Key.Amount * 100 / entityInfo.TotalDamage >= lowDpsThreshold ? new StringBuilder(content) : new StringBuilder(lowDpsContent);
                    x.Value.ToList().ForEach(z => currentContent.Replace(z.Key, z.Value.PadRight(placeholderMono[z.Key])));
                    dpsmono.Append(currentContent);
                });
            else
                { placeholders.ForEach(x =>
                    {
                        var currentContent = x.Key.Amount * 100 / entityInfo.TotalDamage >= lowDpsThreshold ? new StringBuilder(content) : new StringBuilder(lowDpsContent);
                        x.Value.ToList().ForEach(z => currentContent.Replace(z.Key, z.Value));
                        dpsString.Append(currentContent);
                    });
                dpsmono = dpsString;
                }
            var footerstr=footer.Replace("{debuff_list}", String.Join(" | ",
                    bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.Duration(firstTick, lastTick) > 0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick)).ToList().Select(
                        x => x.Key.ShortName + " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick) / (lastTick - firstTick)) +
                        " (" + TimeSpan.FromTicks(x.Value.Duration(firstTick, lastTick)).ToString(@"mm\:ss") + ") ")
                )).Replace("{debuff_list_p}", String.Join(" | ",
                    bossDebuff.Where(x => x.Key.Id != 8888888 && x.Value.Duration(firstTick, lastTick) > 0).OrderByDescending(x => x.Value.Duration(firstTick, lastTick)).ToList().Select(
                        x => x.Key.ShortName + " " + FormatHelpers.Instance.FormatPercent((double)x.Value.Duration(firstTick, lastTick) / (lastTick - firstTick)))
                ));
            dpsString.Append(footerstr);
            dpsmono.Append(footerstr);
            var paste = dpsString.ToString();
            var monoPaste = dpsmono.ToString();
            while (paste.Contains(" \\")) paste = paste.Replace(" \\", "\\");
            while (monoPaste.Contains(" \\")) monoPaste = monoPaste.Replace(" \\", "\\");
            monoPaste = monoPaste.Replace("\\", Environment.NewLine);
            return new Tuple<string,string>(paste ,monoPaste);
        }
コード例 #33
0
        public void Update(StatsSummary nstatsSummary, Database.Structures.Skills nskills, List <NpcEntity> nentities,
                           bool ntimedEncounter, AbnormalityStorage nabnormals,
                           ConcurrentDictionary <string, NpcEntity> nbossHistory, List <ChatMessage> nchatbox, int npacketWaiting)
        {
            NetworkController.UpdateUiHandler changeUi =
                delegate(StatsSummary statsSummary, Database.Structures.Skills skills, List <NpcEntity> entities,
                         bool timedEncounter,
                         AbnormalityStorage abnormals, ConcurrentDictionary <string, NpcEntity> bossHistory,
                         List <ChatMessage> chatbox, int packetWaiting)
            {
                UpdateComboboxEncounter(entities, statsSummary.EntityInformation.Entity);
                _entityStats.Update(statsSummary.EntityInformation, abnormals);
                _windowHistory.Update(bossHistory);
                _chatbox.Update(chatbox);
                _systemTray.UpdatePacketWaiting(packetWaiting);

                PartyDps.Content =
                    FormatHelpers.Instance.FormatValue(statsSummary.EntityInformation.Interval == 0
                            ? statsSummary.EntityInformation.TotalDamage
                            : statsSummary.EntityInformation.TotalDamage * TimeSpan.TicksPerSecond /
                                                       statsSummary.EntityInformation.Interval) + LP.PerSecond;
                var visiblePlayerStats = new HashSet <Player>();
                var statsDamage        = statsSummary.PlayerDamageDealt;
                var statsHeal          = statsSummary.PlayerHealDealt;
                foreach (var playerStats in statsDamage)
                {
                    PlayerStats playerStatsControl;
                    Controls.TryGetValue(playerStats.Source, out playerStatsControl);
                    if (playerStats.Amount == 0)
                    {
                        continue;
                    }

                    visiblePlayerStats.Add(playerStats.Source);
                    if (playerStatsControl != null)
                    {
                        continue;
                    }
                    playerStatsControl = new PlayerStats(playerStats,
                                                         statsHeal.FirstOrDefault(x => x.Source == playerStats.Source),
                                                         statsSummary.EntityInformation, skills, abnormals.Get(playerStats.Source));
                    Controls.Add(playerStats.Source, playerStatsControl);
                }

                var invisibleControls = Controls.Where(x => !visiblePlayerStats.Contains(x.Key)).ToList();
                foreach (var invisibleControl in invisibleControls)
                {
                    Controls[invisibleControl.Key].CloseSkills();
                    Controls.Remove(invisibleControl.Key);
                }

                TotalDamage.Content = FormatHelpers.Instance.FormatValue(statsSummary.EntityInformation.TotalDamage);
                var interval = TimeSpan.FromSeconds(statsSummary.EntityInformation.Interval / TimeSpan.TicksPerSecond);
                Timer.Content = interval.ToString(@"mm\:ss");

                Players.Items.Clear();

                foreach (var item in statsDamage)
                {
                    if (!Controls.ContainsKey(item.Source))
                    {
                        continue;
                    }
                    if (Players.Items.Contains(Controls[item.Source]))
                    {
                        BasicTeraData.LogError("duplicate playerinfo: \r\n" + String.Join("\r\n ", statsDamage.Select(x => x.Source.ToString() + " -> " + x.Target + ": " + x.Amount)), false, true);
                        continue;
                    }
                    Players.Items.Add(Controls[item.Source]);
                    Controls[item.Source].Repaint(item,
                                                  statsHeal.FirstOrDefault(x => x.Source == item.Source),
                                                  statsSummary.EntityInformation, skills, abnormals.Get(item.Source), timedEncounter);
                }

                if (BasicTeraData.Instance.WindowData.InvisibleUi)
                {
                    if (Controls.Count > 0 && !ForceWindowVisibilityHidden)
                    {
                        Visibility = Visibility.Visible;
                    }
                    if (Controls.Count == 0)
                    {
                        Visibility = Visibility.Hidden;
                    }
                }
                else
                {
                    if (!ForceWindowVisibilityHidden)
                    {
                        Visibility = Visibility.Visible;
                    }
                }
            };
            Dispatcher.Invoke(changeUi, nstatsSummary, nskills, nentities, ntimedEncounter, nabnormals, nbossHistory,
                              nchatbox, npacketWaiting);
        }
コード例 #34
0
ファイル: DataExporter.cs プロジェクト: gkfnaleks/ShinraMeter
        public static void ToTeraDpsApi(SDespawnNpc despawnNpc, AbnormalityStorage abnormals)
        {
            if (!BasicTeraData.Instance.WindowData.Excel &&
                (string.IsNullOrEmpty(BasicTeraData.Instance.WindowData.TeraDpsToken) || string.IsNullOrEmpty(BasicTeraData.Instance.WindowData.TeraDpsUser)))
            {
                return;
            }

            if (!despawnNpc.Dead)
            {
                return;
            }

            var entity = DamageTracker.Instance.GetEntity(despawnNpc.Npc);

            if (!entity.IsBoss)
            {
                return;
            }

            bool timedEncounter = false;

            //Nightmare desolarus
            if (entity.NpcE.Info.HuntingZoneId == 759 && entity.NpcE.Info.TemplateId == 1003)
            {
                timedEncounter = true;
            }

            var interval = DamageTracker.Instance.Interval(entity);

            if (interval == 0)
            {
                return;
            }
            var stats       = DamageTracker.Instance.GetPlayerStats();
            var firstHit    = DamageTracker.Instance.FirstHit(entity);
            var lastHit     = DamageTracker.Instance.LastHit(entity);
            var entities    = DamageTracker.Instance.GetEntityStats();
            var totaldamage = DamageTracker.Instance.TotalDamage(entity, timedEncounter);
            var partyDps    = DamageTracker.Instance.PartyDps(entity, timedEncounter);

            var teradpsData = new EncounterBase();

            teradpsData.areaId        = entity.NpcE.Info.HuntingZoneId + "";
            teradpsData.bossId        = entity.NpcE.Info.TemplateId + "";
            teradpsData.fightDuration = interval + "";
            teradpsData.partyDps      = partyDps + "";

            foreach (var debuff in abnormals.Get(entity.NpcE))
            {
                long percentage = (debuff.Value.Duration(firstHit, lastHit) * 100 / interval);
                if (percentage == 0)
                {
                    continue;
                }
                teradpsData.debuffUptime.Add(new KeyValuePair <string, string>(
                                                 debuff.Key.Id + "", percentage + ""
                                                 ));
            }

            foreach (var user in stats)
            {
                var teradpsUser = new Members();
                var damage      = user.Dealt.Damage(entity, timedEncounter);
                teradpsUser.playerTotalDamage = damage + "";

                if (damage <= 0)
                {
                    continue;
                }

                var buffs = abnormals.Get(user.Player);
                teradpsUser.playerClass                 = user.Class.ToString();
                teradpsUser.playerName                  = user.Name;
                teradpsUser.playerServer                = BasicTeraData.Instance.Servers.GetServerName(user.Player.ServerId);
                teradpsUser.playerAverageCritRate       = user.Dealt.CritRate(entity, timedEncounter) + "";
                teradpsUser.playerDps                   = user.Dealt.GlobalDps(entity, timedEncounter, interval) + "";
                teradpsUser.playerTotalDamagePercentage = user.Dealt.DamageFraction(entity, totaldamage, timedEncounter) + "";

                var death = buffs.Death;
                teradpsUser.playerDeaths        = death.Count(firstHit, lastHit) + "";
                teradpsUser.playerDeathDuration = death.Duration(firstHit, lastHit) + "";

                foreach (var buff in buffs.Times)
                {
                    long percentage = (buff.Value.Duration(user.Dealt.GetFirstHit(entity), user.Dealt.GetLastHit(entity)) * 100 / interval);
                    if (percentage == 0)
                    {
                        continue;
                    }
                    teradpsUser.buffUptime.Add(new KeyValuePair <string, string>(
                                                   buff.Key.Id + "", percentage + ""
                                                   ));
                }
                Dictionary <Skills.Skill.Skill, SkillStats> notimedskills;
                if (timedEncounter)
                {
                    notimedskills = NoTimedSkills(user.Dealt.GetSkillsByTime(entity));
                }
                else
                {
                    notimedskills = NoTimedSkills(user.Dealt.GetSkills(entity));
                }

                foreach (var skill in notimedskills)
                {
                    var skillLog    = new SkillLog();
                    var skilldamage = skill.Value.Damage;

                    skillLog.skillAverageCrit   = skill.Value.DmgAverageCrit + "";
                    skillLog.skillAverageWhite  = skill.Value.DmgAverageHit + "";
                    skillLog.skillCritRate      = skill.Value.CritRateDmg + "";
                    skillLog.skillDamagePercent = skill.Value.DamagePercentage(entity, timedEncounter) + "";
                    skillLog.skillHighestCrit   = skill.Value.DmgBiggestCrit + "";
                    skillLog.skillHits          = skill.Value.HitsDmg + "";
                    skillLog.skillId            = skill.Key.SkillId.ElementAt(0) + "";
                    skillLog.skillLowestCrit    = skill.Value.DmgLowestCrit + "";
                    skillLog.skillTotalDamage   = skilldamage + "";

                    if (skilldamage == 0)
                    {
                        continue;
                    }
                    teradpsUser.skillLog.Add(skillLog);
                }
                teradpsData.members.Add(teradpsUser);
            }

            if (BasicTeraData.Instance.WindowData.Excel)
            {
                var excelThread = new Thread(() => ExcelExport.ExcelSave(teradpsData));
                excelThread.Start();
            }
            if (string.IsNullOrEmpty(BasicTeraData.Instance.WindowData.TeraDpsToken) || string.IsNullOrEmpty(BasicTeraData.Instance.WindowData.TeraDpsUser))
            {
                return;
            }
            string json       = JsonConvert.SerializeObject(teradpsData);
            var    sendThread = new Thread(() => Send(entity, json, 3));

            sendThread.Start();
            var jsonThread = new Thread(() => JsonExport(json));

            jsonThread.Start();
        }
コード例 #35
0
ファイル: CopyPaste.cs プロジェクト: stas2130/ShinraMeter
        public static string Copy(StatsSummary statsSummary, Skills skills, AbnormalityStorage abnormals,
                                  bool timedEncounter, string header, string content,
                                  string footer, string orderby, string order)
        {
            //stop if nothing to paste
            var entityInfo   = statsSummary.EntityInformation;
            var playersInfos = statsSummary.PlayerDamageDealt;
            var firstTick    = entityInfo.BeginTime;
            var lastTick     = entityInfo.EndTime;
            var firstHit     = firstTick / TimeSpan.TicksPerSecond;
            var lastHit      = lastTick / TimeSpan.TicksPerSecond;
            var heals        = statsSummary.PlayerHealDealt;

            playersInfos.RemoveAll(x => x.Amount == 0);

            IEnumerable <PlayerDamageDealt> playerInfosOrdered;

            if (order == "ascending")
            {
                switch (orderby)
                {
                case "damage_received":
                    playerInfosOrdered =
                        playersInfos.OrderBy(
                            playerInfo =>
                            skills.DamageReceived(playerInfo.Source.User.Id, entityInfo.Entity,
                                                  timedEncounter));
                    break;

                case "name":
                    playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.Source.Name);
                    break;

                case "damage_percentage":
                case "damage_dealt":
                case "dps":
                    playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.Amount);
                    break;

                case "crit_rate":
                    playerInfosOrdered = playersInfos.OrderBy(playerInfo => playerInfo.CritRate);
                    break;

                case "hits_received":
                    playerInfosOrdered =
                        playersInfos.OrderBy(
                            playerInfo =>
                            skills.HitsReceived(playerInfo.Source.User.Id, entityInfo.Entity, timedEncounter));
                    break;

                default:
                    Console.WriteLine("wrong value for orderby");
                    throw new Exception("wrong value for orderby");
                }
            }
            else
            {
                switch (orderby)
                {
                case "damage_received":
                    playerInfosOrdered =
                        playersInfos.OrderByDescending(
                            playerInfo =>
                            skills.DamageReceived(playerInfo.Source.User.Id, entityInfo.Entity,
                                                  timedEncounter));
                    break;

                case "name":
                    playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.Source.Name);
                    break;

                case "damage_percentage":
                case "damage_dealt":
                case "dps":
                    playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.Amount);
                    break;

                case "crit_rate":
                    playerInfosOrdered = playersInfos.OrderByDescending(playerInfo => playerInfo.CritRate);
                    break;

                case "hits_received":
                    playerInfosOrdered =
                        playersInfos.OrderByDescending(
                            playerInfo =>
                            skills.HitsReceived(playerInfo.Source.User.Id, entityInfo.Entity, timedEncounter));
                    break;

                default:
                    Console.WriteLine("wrong value for orderby");
                    throw new Exception("wrong value for orderby");
                }
            }

            var dpsString = header;

            var name = entityInfo.Entity?.Info.Name ?? "";
            AbnormalityDuration enrage;

            abnormals.Get(entityInfo.Entity).TryGetValue(BasicTeraData.Instance.HotDotDatabase.Get(8888888), out enrage);
            var enrageperc = lastTick - firstTick == 0
                ? 0
                : (double)(enrage?.Duration(firstTick, lastTick) ?? 0) / (lastTick - firstTick);

            dpsString = dpsString.Replace("{encounter}", name);
            var interval = TimeSpan.FromSeconds(lastHit - firstHit);

            dpsString = dpsString.Replace("{timer}", interval.ToString(@"mm\:ss"));
            dpsString = dpsString.Replace("{partyDps}",
                                          FormatHelpers.Instance.FormatValue(lastHit - firstHit > 0
                    ? entityInfo.TotalDamage / (lastHit - firstHit)
                    : 0) + LP.PerSecond);
            dpsString = dpsString.Replace("{enrage}", FormatHelpers.Instance.FormatPercent(enrageperc));

            foreach (var playerStats in playerInfosOrdered)
            {
                var currentContent = content;

                var buffs = abnormals.Get(playerStats.Source);
                AbnormalityDuration slaying;
                var    firstOrDefault = heals.FirstOrDefault(x => x.Source == playerStats.Source);
                double healCritrate   = 0;
                if (firstOrDefault != null)
                {
                    healCritrate = firstOrDefault.CritRate;
                }
                buffs.Times.TryGetValue(BasicTeraData.Instance.HotDotDatabase.Get(8888889), out slaying);
                var slayingperc = lastTick - firstTick == 0
                    ? 0
                    : (double)(slaying?.Duration(firstTick, lastTick) ?? 0) / (lastTick - firstTick);
                currentContent = currentContent.Replace("{slaying}", FormatHelpers.Instance.FormatPercent(slayingperc));
                currentContent = currentContent.Replace("{dps}",
                                                        FormatHelpers.Instance.FormatValue(playerStats.Interval == 0 ? playerStats.Amount : playerStats.Amount * TimeSpan.TicksPerSecond / playerStats.Interval) +
                                                        "/s");
                currentContent = currentContent.Replace("{global_dps}",
                                                        FormatHelpers.Instance.FormatValue(entityInfo.Interval == 0 ? playerStats.Amount : playerStats.Amount * TimeSpan.TicksPerSecond / entityInfo.Interval) +
                                                        "/s");
                currentContent = currentContent.Replace("{interval}", playerStats.Interval + LP.Seconds);
                currentContent = currentContent.Replace("{damage_dealt}",
                                                        FormatHelpers.Instance.FormatValue(playerStats.Amount));
                currentContent = currentContent.Replace("{class}", playerStats.Source.Class + "");
                currentContent = currentContent.Replace("{fullname}", playerStats.Source.FullName);
                currentContent = currentContent.Replace("{name}", playerStats.Source.Name);
                currentContent = currentContent.Replace("{deaths}", buffs.Death.Count(firstTick, lastTick) + "");
                currentContent = currentContent.Replace("{death_duration}",
                                                        TimeSpan.FromTicks(buffs.Death.Duration(firstTick, lastTick)).ToString(@"mm\:ss"));
                currentContent = currentContent.Replace("{aggro}",
                                                        buffs.Aggro(entityInfo.Entity).Count(firstTick, lastTick) + "");
                currentContent = currentContent.Replace("{aggro_duration}",
                                                        TimeSpan.FromTicks(buffs.Aggro(entityInfo.Entity).Duration(firstTick, lastTick))
                                                        .ToString(@"mm\:ss"));
                currentContent = currentContent.Replace("{damage_percentage}",
                                                        playerStats.Amount * 100 / entityInfo.TotalDamage + "%");
                currentContent = currentContent.Replace("{crit_rate}", playerStats.CritRate + "%");
                currentContent = currentContent.Replace("{crit_rate_heal}",
                                                        healCritrate + "%");
                currentContent = currentContent.Replace("{biggest_crit}",
                                                        FormatHelpers.Instance.FormatValue(skills.BiggestCrit(playerStats.Source.User.Id, entityInfo.Entity,
                                                                                                              timedEncounter)));
                currentContent = currentContent.Replace("{damage_received}",
                                                        FormatHelpers.Instance.FormatValue(skills.DamageReceived(playerStats.Source.User.Id,
                                                                                                                 entityInfo.Entity, timedEncounter)));
                currentContent = currentContent.Replace("{hits_received}",
                                                        FormatHelpers.Instance.FormatValue(skills.HitsReceived(playerStats.Source.User.Id,
                                                                                                               entityInfo.Entity, timedEncounter)));

                dpsString += currentContent;
            }
            dpsString += footer;
            return(dpsString);
        }
コード例 #36
0
        private static ExtendedStats GenerateStats(SDespawnNpc despawnNpc, AbnormalityStorage abnormals)
        {
            if (!despawnNpc.Dead)
            {
                return(null);
            }

            var entity = DamageTracker.Instance.GetEntity(despawnNpc.Npc);

            if (!entity.IsBoss || !DamageTracker.Instance.EntitiesStats.ContainsKey(entity))
            {
                return(null);
            }

            bool timedEncounter = false;

            //Nightmare desolarus
            if (entity.NpcE.Info.HuntingZoneId == 759 && entity.NpcE.Info.TemplateId == 1003)
            {
                timedEncounter = true;
            }

            var firstTick = DamageTracker.Instance.EntitiesStats[entity].FirstHit;
            var lastTick  = DamageTracker.Instance.EntitiesStats[entity].LastHit;
            var interTick = lastTick - firstTick;
            var interval  = interTick / TimeSpan.TicksPerSecond;

            if (interval == 0)
            {
                return(null);
            }
            var totaldamage = DamageTracker.Instance.TotalDamage(entity, timedEncounter);
            var partyDps    = TimeSpan.TicksPerSecond * totaldamage / interTick;

            var teradpsData   = new EncounterBase();
            var extendedStats = new ExtendedStats();
            var stats         = DamageTracker.Instance.GetPlayerStats();
            var _abnormals    = abnormals.Clone(entity.NpcE, firstTick, lastTick);

            extendedStats.Entity      = entity.NpcE;
            extendedStats.BaseStats   = teradpsData;
            extendedStats.FirstTick   = firstTick;
            extendedStats.LastTick    = lastTick;
            teradpsData.areaId        = entity.NpcE.Info.HuntingZoneId + "";
            teradpsData.bossId        = entity.NpcE.Info.TemplateId + "";
            teradpsData.fightDuration = interval + "";
            teradpsData.partyDps      = partyDps + "";
            extendedStats.Debuffs     = _abnormals.Get(entity.NpcE);

            foreach (var debuff in extendedStats.Debuffs)
            {
                long percentage = (debuff.Value.Duration(firstTick, lastTick) * 100 / interTick);
                if (percentage == 0)
                {
                    continue;
                }
                teradpsData.debuffUptime.Add(new KeyValuePair <string, string>(
                                                 debuff.Key.Id + "", percentage + ""
                                                 ));
            }

            foreach (var user in stats)
            {
                var teradpsUser = new Members();
                var damage      = user.Dealt.Damage(entity, timedEncounter);
                teradpsUser.playerTotalDamage = damage + "";

                if (damage <= 0)
                {
                    continue;
                }

                var buffs = _abnormals.Get(user.Player);
                teradpsUser.playerClass           = user.Class.ToString();
                teradpsUser.playerName            = user.Name;
                teradpsUser.playerServer          = BasicTeraData.Instance.Servers.GetServerName(user.Player.ServerId);
                teradpsUser.playerAverageCritRate = user.Dealt.CritRate(entity, timedEncounter) + "";
                teradpsUser.healCrit  = user.IsHealer ? user.Dealt.CritRateHeal(entity, timedEncounter) + "" : null;
                teradpsUser.playerDps = TimeSpan.TicksPerSecond * damage / interTick + "";
                teradpsUser.playerTotalDamagePercentage = user.Dealt.DamageFraction(entity, totaldamage, timedEncounter) + "";

                var death = buffs.Death;
                teradpsUser.playerDeaths        = death.Count(firstTick, lastTick) + "";
                teradpsUser.playerDeathDuration = death.Duration(firstTick, lastTick) / TimeSpan.TicksPerSecond + "";

                var aggro = buffs.Aggro(entity.NpcE);
                teradpsUser.aggro = 100 * aggro.Duration(firstTick, lastTick) / interTick + "";

                foreach (var buff in buffs.Times)
                {
                    long percentage = (buff.Value.Duration(firstTick, lastTick) * 100 / interTick);
                    if (percentage == 0)
                    {
                        continue;
                    }
                    teradpsUser.buffUptime.Add(new KeyValuePair <string, string>(
                                                   buff.Key.Id + "", percentage + ""
                                                   ));
                }
                var serverPlayerName = $"{teradpsUser.playerServer}_{teradpsUser.playerName}";
                extendedStats.PlayerSkills.Add(serverPlayerName, timedEncounter ? user.Dealt.GetSkillsByTime(entity) : user.Dealt.GetSkills(entity));
                extendedStats.PlayerBuffs.Add(serverPlayerName, buffs);
                var notimedskills = NoTimedSkills(extendedStats.PlayerSkills[serverPlayerName]);

                foreach (var skill in notimedskills)
                {
                    var skillLog    = new SkillLog();
                    var skilldamage = skill.Value.Damage;

                    skillLog.skillAverageCrit   = skill.Value.DmgAverageCrit + "";
                    skillLog.skillAverageWhite  = skill.Value.DmgAverageHit + "";
                    skillLog.skillCritRate      = skill.Value.CritRateDmg + "";
                    skillLog.skillDamagePercent = skill.Value.DamagePercentage(entity, timedEncounter) + "";
                    skillLog.skillHighestCrit   = skill.Value.DmgBiggestCrit + "";
                    skillLog.skillHits          = skill.Value.HitsDmg + "";
                    skillLog.skillId            = BasicTeraData.Instance.SkillDatabase.GetSkillByPetName(skill.Key.NpcInfo?.Name, user.Player.RaceGenderClass)?.Id.ToString() ?? skill.Key.SkillId.ElementAt(0).ToString();
                    skillLog.skillLowestCrit    = skill.Value.DmgLowestCrit + "";
                    skillLog.skillTotalDamage   = skilldamage + "";

                    if (skilldamage == 0)
                    {
                        continue;
                    }
                    teradpsUser.skillLog.Add(skillLog);
                }
                teradpsData.members.Add(teradpsUser);
            }
            return(extendedStats);
        }