@if (FaviconBytes != null)
{
    <img src="@_faviconDataUrl" style="width: @(Width)px;" class="rounded-lg w-28 @(Padding ? "mb-4 sm:mb-0 xl:mb-4 2xl:mb-0" : "")" alt="Favicon" />
}
else
{
    <img src="img/service-placeholder.webp" style="width: @(Width)px;" class="@(Padding ? "mb-4 sm:mb-0 xl:mb-4 2xl:mb-0" : "")" alt="Favicon" />
}

@code {
    /// <summary>
    /// Byte[] of the favicon.
    /// </summary>
    [Parameter]
    public byte[]? FaviconBytes { get; set; }

    /// <summary>
    /// The width (in pixels) to show the icon as. Defaults to 50px.
    /// </summary>
    [Parameter]
    public int Width { get; set; } = 50;

    /// <summary>
    /// Boolean indicating whether to add padding to the icon. Defaults to false.
    /// </summary>
    [Parameter]
    public bool Padding { get; set; }

    /// <summary>
    /// The data URL of the favicon.
    /// </summary>
    private string? _faviconDataUrl;

    /// <inheritdoc />
    protected override void OnParametersSet()
    {
        if (FaviconBytes is not null)
        {
            string mimeType = DetectMimeType(FaviconBytes);
            string base64String = Convert.ToBase64String(FaviconBytes);
            _faviconDataUrl = $"data:{mimeType};base64,{base64String}";
        }
    }

    /// <summary>
    /// Detect the mime type of the favicon.
    /// </summary>
    /// <param name="bytes">The bytes of the favicon.</param>
    /// <returns>The mime type of the favicon.</returns>
    private static string DetectMimeType(byte[] bytes)
    {
        // Check for SVG.
        if (bytes.Length >= 5)
        {
            string header = System.Text.Encoding.ASCII.GetString(bytes.Take(5).ToArray()).ToLower();
            if (header.Contains("<?xml") || header.Contains("<svg"))
            {
                return "image/svg+xml";
            }
        }

        // Check for ICO.
        if (bytes.Length >= 4 &&
            bytes[0] == 0x00 && bytes[1] == 0x00 &&
            bytes[2] == 0x01 && bytes[3] == 0x00)
        {
            return "image/x-icon";
        }

        // Check for PNG.
        if (bytes.Length >= 4 &&
            bytes[0] == 0x89 && bytes[1] == 0x50 &&
            bytes[2] == 0x4E && bytes[3] == 0x47)
        {
            return "image/png";
        }

        // Default to x-icon if unknown.
        return "image/x-icon";
    }
}
