예제 #1
0
        public async Task <BossLevelState> ReportBossDamage(int startLevel, long startXp, bool useHealAbility, int damageToBoss, int damageTaken)
        {
            for (int i = 0; i < 5; i++)
            {
                try
                {
                    var message = $"{{action}}Reporting boss damage {{value}}+{damageToBoss.ToString("#,##0")}";
                    if (damageTaken > 0)
                    {
                        message += $"{{action}}, {{negvalue}}-{damageTaken.ToString("#,##0")}";
                    }
                    if (useHealAbility)
                    {
                        message += $"{{action}}, {{value}}+Heal";
                    }
                    message += $"{{action}}...";
                    this.Logger?.LogMessage(message);

                    var response = await SaliensApi.ReportBossDamageAsync(this.Token, useHealAbility, damageToBoss, damageTaken);

                    if (response.BossStatus == null)
                    {
                        return(BossLevelState.WaitingForPlayers);
                    }

                    BossPlayer currentPlayer = null;
                    var        bossHpColor   = MathUtils.ScaleColor(response.BossStatus.BossMaxHp - response.BossStatus.BossHp, response.BossStatus.BossMaxHp, new[] { "{svlow}", "{slow}", "{smed}", "{shigh}", "{svhigh}" });
                    this.Logger?.LogMessage($"{bossHpColor}Boss HP: {response.BossStatus.BossHp.ToString("#,##0")}/{response.BossStatus.BossMaxHp.ToString("#,##0")}{{reset}} - {{lasers}}{response.NumLaserUses} lasers{{reset}} - {{heals}}{response.NumTeamHeals} heals");
                    foreach (var player in response.BossStatus.BossPlayers.OrderBy(p => p.Name))
                    {
                        var playerStartLevel = player.LevelOnJoin;
                        long.TryParse(player.ScoreOnJoin, out long playerStartXp);

                        var isCurrentPlayer = playerStartLevel == startLevel && playerStartXp == startXp;
                        if (isCurrentPlayer)
                        {
                            currentPlayer = player;
                        }
                        var playerColor = isCurrentPlayer ? "{player}" : "{reset}";
                        var hpColor     = MathUtils.ScaleColor(player.MaxHp - player.Hp, player.MaxHp, new[] { "{svlow}", "{slow}", "{smed}", "{shigh}", "{svhigh}" });
                        this.Logger?.LogMessage($"{playerColor}{(player.Name.Length > 16 ? player.Name.Substring(0, 16) : player.Name).PadLeft(16)}: " +
                                                $"{hpColor}HP {player.Hp.ToString("#,##0").PadLeft(7)}/{player.MaxHp.ToString("#,##0").PadLeft(7)}{playerColor} - " +
                                                $"XP {player.XpEarned.ToString("#,##0").PadLeft(9)}/{(playerStartXp + player.XpEarned).ToString("#,##0").PadLeft(12)}");
                    }

                    if (response.GameOver && currentPlayer != null && long.TryParse(this.PlayerInfo.Score, out long oldScore))
                    {
                        // States
                        this.PlayerInfo.Score          = (oldScore + currentPlayer.XpEarned).ToString();
                        this.PlayerInfo.Level          = currentPlayer.NewLevel;
                        this.PlayerInfo.NextLevelScore = currentPlayer.NextLevelScore;
                    }
                    return(response.GameOver ? BossLevelState.GameOver : BossLevelState.Active);
                }
                catch (SaliensApiException ex)
                {
                    switch (ex.EResult)
                    {
                    case EResult.Fail:
                    case EResult.Busy:
                    case EResult.RateLimitExceeded:
                        this.Logger?.LogMessage($"{{warn}}Failed to report boss damage: {ex.Message} - Giving it a second ({i + 1}/5)...");
                        await Task.Delay(1000);

                        continue;

                    case EResult.Expired:
                    case EResult.NoMatch:
                    default:
                        this.Logger?.LogMessage($"{{warn}}Failed to report boss damage: {ex.Message}");
                        ResetState();
                        throw;
                    }
                }
                catch (WebException ex)
                {
                    this.Logger?.LogMessage($"{{warn}}Failed to report boss damage: {ex.Message} - Giving it a second ({i + 1}/5)...");
                    await Task.Delay(1000);

                    continue;
                }
            }

            // States, only set when failed
            ResetState();
            void ResetState()
            {
                this.ActiveZone = null;
                this.PlayerInfo.ActiveBossGame     = null;
                this.PlayerInfo.ActiveZonePosition = null;
                this.State = BotState.ForcedZoneLeave;
            }

            return(BossLevelState.Error);
        }