@typeparam TBind

<div @onclick="Toggle" class="dropdown-root">
    @CurrentIcon
</div>

@if (Visible)
{
    <div class="dropdown-menu">
        @foreach (var entry in Elements)
        {
            <DropdownElement TBind="TBind" OnSelect="UpdateSelected" Icon="entry.Icon" Content="entry.Content" Selection="entry.Selection"/>
        }
    </div>
}

@code {
    private                                      TBind                               _value = default!;
    [Parameter] [EditorRequired] public required IEnumerable<DropdownElement<TBind>> Elements { get; set; }

    [Parameter]
    [EditorRequired]
    #pragma warning disable BL0007 // While this implementation is suboptimal, this is technically fine. Should be reworked.
    public required TBind Value
    {
        get => _value;
        set
        {
            _value           = value;
            CurrentSelection = Elements.First(element => element.Selection != null && element.Selection.Equals(value));
            CurrentIcon      = CurrentSelection.Icon;
        }
    }
    #pragma warning restore BL0007

    [Parameter] public EventCallback<TBind>    ValueChanged     { get; set; }
    private            DropdownElement<TBind>? CurrentSelection { get; set; }
    private            RenderFragment?         CurrentIcon      { get; set; }
    private            bool                    Visible          { get; set; } = false;

    private void UpdateSelected(DropdownElement<TBind> element)
    {
        CurrentSelection = element;
        CurrentIcon      = CurrentSelection.Icon;
        ValueChanged.InvokeAsync(element.Selection);
        Visible = false;
    }

    private void Toggle()
    {
        Visible = !Visible;
    }

    protected override void OnInitialized()
    {
        UpdateSelected(Elements.FirstOrDefault() ?? throw new InvalidOperationException());
    }
}