@using System
@using System.Collections.Generic
@using System.Diagnostics.CodeAnalysis
@using RolemasterDb.App.Domain
@using RolemasterDb.App.Features
@using PowerPointModifierNotation = RolemasterDb.CriticalParsing.PowerPointModifierNotation

@if (EffectiveEffects.Count > 0)
{
    <div class="affix-badge-list">
        @foreach (var effect in EffectiveEffects)
        {
            if (TryRenderEffect(effect, out var info, out var valueText))
            {
                <span class="affix-badge" title="@info.Tooltip">
                    <span class="affix-badge-symbol">@info.Symbol</span>
                    @if (!string.IsNullOrWhiteSpace(valueText))
                    {
                        <span class="affix-badge-value">@valueText</span>
                    }
                </span>
            }
            else
            {
                <span class="affix-badge affix-badge-fallback" title="@effect.EffectCode">
                    @FormatFallback(effect)
                </span>
            }
        }
    </div>
}

@code {
    [Parameter]
    public IReadOnlyList<CriticalEffectLookupResponse>? Effects { get; set; }

    private IReadOnlyList<CriticalEffectLookupResponse> EffectiveEffects =>
        Effects ?? Array.Empty<CriticalEffectLookupResponse>();

    private static bool TryRenderEffect(
        CriticalEffectLookupResponse effect,
        [NotNullWhen(true)] out AffixDisplayInfo? info,
        out string valueText)
    {
        if (!AffixDisplayMap.TryGet(effect.EffectCode, out info))
        {
            valueText = string.Empty;
            return false;
        }

        valueText = FormatAffixValue(effect);
        return true;
    }

    private static string FormatAffixValue(CriticalEffectLookupResponse effect) =>
        effect.EffectCode switch
        {
            CriticalEffectCodes.StunnedRounds
                or CriticalEffectCodes.MustParryRounds
                or CriticalEffectCodes.NoParryRounds => effect.DurationRounds?.ToString() ?? string.Empty,
            CriticalEffectCodes.BleedPerRound => effect.PerRound?.ToString() ?? string.Empty,
            CriticalEffectCodes.DirectHits => $"+{effect.ValueInteger?.ToString() ?? string.Empty}",
            CriticalEffectCodes.FoePenalty
                or CriticalEffectCodes.AttackerBonusNextRound => effect.Modifier?.ToString() ?? string.Empty,
            CriticalEffectCodes.PowerPointModifier => PowerPointModifierNotation.FormatSignedExpression(effect.ValueExpression) ?? string.Empty,
            _ => effect.ValueInteger?.ToString()
                  ?? effect.Modifier?.ToString()
                  ?? effect.ValueExpression
                  ?? effect.SourceText
                  ?? string.Empty
        };

    private static string FormatFallback(CriticalEffectLookupResponse effect) =>
        effect.SourceText ?? effect.EffectCode;
}
