@page "/blocks/notifications"
@namespace Lumeo.Docs.Pages.Patterns
@using Lumeo.Services
@inject ToastService ToastService

<PageTitle>Notifications — Lumeo Patterns</PageTitle>

<PageHeader Title="Notifications" Description="A full notification center with tabbed inbox (All / Mentions / Activity / Followers / Security), time-grouped items with unread indicators, preference toggles, and live toast demos." />

<Stack Gap="6">

    <ComponentDemo Title="Notification Center" Code="@_code">
        <Grid Class="w-full min-w-[700px] grid-cols-1 lg:grid-cols-5 gap-6">

            <!-- Left: Preferences + Try It -->
            <Stack Gap="4" Class="lg:col-span-2">

                <!-- Preferences Card -->
                <Card Class="border-border/40">
                    <CardHeader>
                        <Flex Class="items-center gap-2.5">
                            <Flex Class="h-8 w-8 items-center justify-center rounded-md bg-primary/10 shrink-0">
                                <DynamicIcon Name="Bell" Class="h-4 w-4 text-primary" />
                            </Flex>
                            <Stack Class="gap-0">
                                <Heading Level="3" Class="text-sm font-semibold text-foreground">Notification Preferences</Heading>
                                <Lumeo.Text Class="text-xs text-muted-foreground">Manage how you're notified</Lumeo.Text>
                            </Stack>
                        </Flex>
                    </CardHeader>
                    <CardContent Class="space-y-1 pt-0">

                        <!-- Master toggle -->
                        <Flex Class="items-center justify-between rounded-lg border border-border/40 bg-muted/30 px-4 py-3">
                            <Flex Class="items-center gap-3">
                                <DynamicIcon Name="Smartphone" Class="h-4 w-4 text-foreground" />
                                <Stack Class="gap-0">
                                    <Lumeo.Text Class="text-sm font-semibold text-foreground">Push Notifications</Lumeo.Text>
                                    <Lumeo.Text Class="text-xs text-muted-foreground">Receive alerts on your devices</Lumeo.Text>
                                </Stack>
                            </Flex>
                            <Switch Size="Switch.SwitchSize.Lg" @bind-Checked="_pushEnabled" />
                        </Flex>

                        <Separator Class="my-3" />

                        <!-- Channel toggles -->
                        <Stack Class="gap-3 px-1">
                            <Flex Class="items-center justify-between">
                                <Flex Class="items-center gap-3">
                                    <DynamicIcon Name="Mail" Class="h-4 w-4 text-muted-foreground" />
                                    <Stack Class="gap-0">
                                        <Lumeo.Text Class="text-sm font-medium text-foreground">Email</Lumeo.Text>
                                        <Lumeo.Text Class="text-xs text-muted-foreground">Digest and transactional emails</Lumeo.Text>
                                    </Stack>
                                </Flex>
                                <Switch @bind-Checked="_emailEnabled" Disabled="@(!_pushEnabled)" />
                            </Flex>
                            <Flex Class="items-center justify-between">
                                <Flex Class="items-center gap-3">
                                    <DynamicIcon Name="MessageSquare" Class="h-4 w-4 text-muted-foreground" />
                                    <Stack Class="gap-0">
                                        <Lumeo.Text Class="text-sm font-medium text-foreground">SMS</Lumeo.Text>
                                        <Lumeo.Text Class="text-xs text-muted-foreground">Critical alerts only</Lumeo.Text>
                                    </Stack>
                                </Flex>
                                <Switch @bind-Checked="_smsEnabled" Disabled="@(!_pushEnabled)" />
                            </Flex>
                        </Stack>

                        <Separator Class="my-3">
                            <Lumeo.Text As="span" Class="px-2 text-xs font-medium text-muted-foreground bg-card">Categories</Lumeo.Text>
                        </Separator>

                        <Stack Class="gap-3 px-1">
                            <Flex Class="items-center justify-between">
                                <Stack Class="gap-0">
                                    <Lumeo.Text Class="text-sm text-foreground">Marketing emails</Lumeo.Text>
                                    <Lumeo.Text Class="text-xs text-muted-foreground">Promos and special offers</Lumeo.Text>
                                </Stack>
                                <Switch Size="Switch.SwitchSize.Sm" @bind-Checked="_marketingEnabled" Disabled="@(!_pushEnabled || !_emailEnabled)" />
                            </Flex>
                            <Flex Class="items-center justify-between">
                                <Stack Class="gap-0">
                                    <Lumeo.Text Class="text-sm text-foreground">Product updates</Lumeo.Text>
                                    <Lumeo.Text Class="text-xs text-muted-foreground">New features and changelogs</Lumeo.Text>
                                </Stack>
                                <Switch Size="Switch.SwitchSize.Sm" @bind-Checked="_updatesEnabled" Disabled="@(!_pushEnabled || !_emailEnabled)" />
                            </Flex>
                            <Flex Class="items-center justify-between">
                                <Stack Class="gap-0">
                                    <Lumeo.Text Class="text-sm text-foreground">Security alerts</Lumeo.Text>
                                    <Lumeo.Text Class="text-xs text-muted-foreground">Sign-ins and suspicious activity</Lumeo.Text>
                                </Stack>
                                <Switch Size="Switch.SwitchSize.Sm" @bind-Checked="_securityEnabled" Disabled="@(!_pushEnabled)" />
                            </Flex>
                        </Stack>

                    </CardContent>
                </Card>

                <!-- Live Demo Card -->
                <Card Class="border-border/40">
                    <CardHeader>
                        <Flex Class="items-center gap-2.5">
                            <Flex Class="h-8 w-8 items-center justify-center rounded-md bg-primary/10 shrink-0">
                                <DynamicIcon Name="Zap" Class="h-4 w-4 text-primary" />
                            </Flex>
                            <Stack Class="gap-0">
                                <Heading Level="3" Class="text-sm font-semibold text-foreground">Try It Live</Heading>
                                <Lumeo.Text Class="text-xs text-muted-foreground">Trigger notification types</Lumeo.Text>
                            </Stack>
                        </Flex>
                    </CardHeader>
                    <CardContent Class="pt-0">
                        <Grid Class="grid-cols-2 gap-2">
                            <Button Variant="Button.ButtonVariant.Outline" Size="Button.ButtonSize.Sm" @onclick="ShowInfo">
                                <DynamicIcon Name="Info" Class="h-3.5 w-3.5 mr-1.5" />
                                Info
                            </Button>
                            <Button Variant="Button.ButtonVariant.Outline" Size="Button.ButtonSize.Sm" @onclick="ShowSuccess">
                                <DynamicIcon Name="CircleCheck" Class="h-3.5 w-3.5 mr-1.5" />
                                Success
                            </Button>
                            <Button Variant="Button.ButtonVariant.Outline" Size="Button.ButtonSize.Sm" @onclick="ShowWarning">
                                <DynamicIcon Name="TriangleAlert" Class="h-3.5 w-3.5 mr-1.5" />
                                Warning
                            </Button>
                            <Button Variant="Button.ButtonVariant.Outline" Size="Button.ButtonSize.Sm" @onclick="ShowWithAction">
                                <DynamicIcon Name="MousePointerClick" Class="h-3.5 w-3.5 mr-1.5" />
                                Action
                            </Button>
                            <Button Variant="Button.ButtonVariant.Outline" Size="Button.ButtonSize.Sm" @onclick="ShowPersistent">
                                <DynamicIcon Name="Pin" Class="h-3.5 w-3.5 mr-1.5" />
                                Persistent
                            </Button>
                            <Button Variant="Button.ButtonVariant.Outline" Size="Button.ButtonSize.Sm" @onclick="ShowPromise">
                                <DynamicIcon Name="RefreshCw" Class="h-3.5 w-3.5 mr-1.5" />
                                Promise
                            </Button>
                        </Grid>
                    </CardContent>
                </Card>

            </Stack>

            <!-- Right: Notification Inbox with Tabs -->
            <Card Class="lg:col-span-3 border-border/40">
                <CardHeader Class="pb-3">
                    <Flex Class="items-center justify-between">
                        <Flex Class="items-center gap-2.5">
                            <Flex Class="h-8 w-8 items-center justify-center rounded-md bg-primary/10 shrink-0">
                                <DynamicIcon Name="Inbox" Class="h-4 w-4 text-primary" />
                            </Flex>
                            <Stack Class="gap-0">
                                <Flex Class="items-center gap-2">
                                    <Heading Level="3" Class="text-sm font-semibold text-foreground">Inbox</Heading>
                                    @if (UnreadCount > 0)
                                    {
                                        <Badge>@UnreadCount new</Badge>
                                    }
                                </Flex>
                                <Lumeo.Text Class="text-xs text-muted-foreground">@VisibleNotifications.Count notification@(VisibleNotifications.Count != 1 ? "s" : "")</Lumeo.Text>
                            </Stack>
                        </Flex>
                        <Button Variant="Button.ButtonVariant.Ghost" Size="Button.ButtonSize.Sm" Class="text-xs text-muted-foreground" @onclick="MarkAllRead">
                            Mark all read
                        </Button>
                    </Flex>
                </CardHeader>

                <!-- Tabs -->
                <div class="px-6 border-b border-border/30 mb-0">
                    <Flex Class="gap-0 -mb-px">
                        @foreach (var tab in _tabs)
                        {
                            var t = tab;
                            <button class="@($"px-3 py-2 text-xs font-medium border-b-2 transition-colors {(_activeTab == t ? "border-primary text-foreground" : "border-transparent text-muted-foreground hover:text-foreground hover:border-border")}")"
                                    @onclick="@(() => _activeTab = t)">
                                @t
                                @{
                                    var tabCount = GetTabUnreadCount(t);
                                }
                                @if (tabCount > 0)
                                {
                                    <span class="ml-1.5 inline-flex items-center justify-center h-4 min-w-4 px-1 rounded-full bg-primary text-primary-foreground text-[10px] font-bold">@tabCount</span>
                                }
                            </button>
                        }
                    </Flex>
                </div>

                <CardContent Class="pt-0">
                    @if (VisibleNotifications.Count == 0)
                    {
                        <Flex Direction="col" Class="items-center justify-center py-16 text-center">
                            <div class="h-14 w-14 rounded-full bg-muted flex items-center justify-center mb-4">
                                <DynamicIcon Name="BellOff" Class="h-7 w-7 text-muted-foreground" />
                            </div>
                            <Lumeo.Text Class="text-sm font-medium text-foreground">All caught up</Lumeo.Text>
                            <Lumeo.Text Class="text-xs text-muted-foreground mt-1">No @(_activeTab == "All" ? "" : _activeTab.ToLower() + " ")notifications right now</Lumeo.Text>
                        </Flex>
                    }
                    else
                    {
                        @foreach (var group in GroupedNotifications)
                        {
                            <Stack Class="mt-3">
                                <Lumeo.Text Class="text-[11px] font-semibold text-muted-foreground uppercase tracking-wide px-1 mb-1">@group.Key</Lumeo.Text>
                                @foreach (var notif in group.Value)
                                {
                                    var n = notif;
                                    <div class="@($"flex items-start gap-3 rounded-lg px-3 py-3 mb-0.5 cursor-pointer transition-colors {(!n.IsRead ? "bg-primary/5 hover:bg-primary/8" : "hover:bg-muted/50")}")"
                                         @onclick="@(() => MarkRead(n))">
                                        <!-- Type icon -->
                                        <div class="@($"h-8 w-8 rounded-full flex items-center justify-center shrink-0 mt-0.5 {n.IconBg}")">
                                            <DynamicIcon Name="@n.Icon" Class="@($"h-4 w-4 {n.IconColor}")" />
                                        </div>
                                        <Stack Class="flex-1 min-w-0 gap-0">
                                            <Flex Class="items-start justify-between gap-2">
                                                <Flex Class="items-center gap-1.5 flex-1 min-w-0">
                                                    @if (!n.IsRead)
                                                    {
                                                        <div class="h-1.5 w-1.5 rounded-full bg-primary shrink-0 mt-0.5"></div>
                                                    }
                                                    <Lumeo.Text Class="text-sm font-medium text-foreground leading-snug truncate">@n.Title</Lumeo.Text>
                                                </Flex>
                                                <Lumeo.Text As="span" Class="text-[11px] text-muted-foreground shrink-0 tabular-nums">@n.Time</Lumeo.Text>
                                            </Flex>
                                            <Lumeo.Text Class="@($"text-xs text-muted-foreground leading-relaxed {(!n.IsRead ? "font-medium" : "")}")">@n.Description</Lumeo.Text>
                                            @if (n.Tags is { Count: > 0 })
                                            {
                                                <Flex Class="flex-wrap gap-1 mt-1.5">
                                                    @foreach (var tag in n.Tags)
                                                    {
                                                        <Badge Variant="Badge.BadgeVariant.Secondary" Class="text-[10px] py-0 px-1.5 h-4 font-normal">@tag</Badge>
                                                    }
                                                </Flex>
                                            }
                                            @if (n.ActionLabel is not null)
                                            {
                                                <Button Variant="Button.ButtonVariant.Outline" Size="Button.ButtonSize.Sm" Class="mt-2 h-6 text-xs w-fit">
                                                    @n.ActionLabel
                                                </Button>
                                            }
                                        </Stack>
                                        <button type="button"
                                                class="h-6 w-6 inline-flex items-center justify-center rounded-md text-muted-foreground hover:text-destructive hover:bg-destructive/10 shrink-0 mt-0.5 transition-colors"
                                                @onclick:stopPropagation="true"
                                                @onclick="@(() => _notifications.Remove(n))">
                                            <DynamicIcon Name="X" Class="h-3 w-3" />
                                        </button>
                                    </div>
                                }
                            </Stack>
                        }
                    }
                </CardContent>
            </Card>

        </Grid>
        <ToastProvider />
    </ComponentDemo>

</Stack>

@code {
    private class NotificationItem
    {
        public int Id { get; init; }
        public string Title { get; init; } = "";
        public string Description { get; init; } = "";
        public string Time { get; init; } = "";
        public string TimeGroup { get; init; } = "";
        public bool IsRead { get; set; }
        public string Tab { get; init; } = "All";
        public string Icon { get; init; } = "Bell";
        public string IconBg { get; init; } = "bg-muted";
        public string IconColor { get; init; } = "text-muted-foreground";
        public List<string>? Tags { get; init; }
        public string? ActionLabel { get; init; }
    }

    private bool _pushEnabled = true;
    private bool _emailEnabled = true;
    private bool _smsEnabled;
    private bool _marketingEnabled;
    private bool _updatesEnabled = true;
    private bool _securityEnabled = true;

    private readonly string[] _tabs = { "All", "Mentions", "Activity", "Followers", "Security" };
    private string _activeTab = "All";

    private List<NotificationItem> _notifications = new()
    {
        new() { Id = 1,  Title = "Deployment successful",      Description = "Production deploy of v2.4.1 completed in 42 seconds. All health checks passed.", Time = "2m",        TimeGroup = "Today",        Tab = "Activity",  Icon = "RocketIcon",      IconBg = "bg-primary/10",     IconColor = "text-primary",     Tags = new() { "production", "v2.4.1" }, IsRead = false },
        new() { Id = 2,  Title = "New sign-in detected",       Description = "A new sign-in from San Francisco, CA on Chrome/macOS. Not you? Secure your account.", Time = "8m",    TimeGroup = "Today",        Tab = "Security",  Icon = "ShieldAlert",     IconBg = "bg-destructive/10", IconColor = "text-destructive", Tags = new() { "security" }, IsRead = false, ActionLabel = "Review activity" },
        new() { Id = 3,  Title = "@sofia.d mentioned you",     Description = "\"Great point by @you — container queries really are a game changer for component libs.\"", Time = "15m", TimeGroup = "Today",  Tab = "Mentions",  Icon = "AtSign",          IconBg = "bg-primary/10",     IconColor = "text-primary",     IsRead = false },
        new() { Id = 4,  Title = "Storage at 85%",             Description = "You're using 8.5 GB of your 10 GB quota. Consider upgrading or removing old files.", Time = "1h",     TimeGroup = "Today",        Tab = "Activity",  Icon = "HardDrive",       IconBg = "bg-warning/10",     IconColor = "text-warning-text", IsRead = false },
        new() { Id = 5,  Title = "William Kim started following you", Description = "William Kim (@wkim) is now following your profile.", Time = "2h",               TimeGroup = "Today",        Tab = "Followers", Icon = "UserPlus",        IconBg = "bg-primary/10",     IconColor = "text-primary",     IsRead = false },
        new() { Id = 6,  Title = "Team invitation",            Description = "Alice Chen invited you to join the Design Systems team.", Time = "4h",                TimeGroup = "Today",        Tab = "Activity",  Icon = "Users",           IconBg = "bg-chart-1/20",     IconColor = "text-chart-1",     IsRead = true, ActionLabel = "Accept invite" },
        new() { Id = 7,  Title = "@jackson.dev mentioned you", Description = "\"Agree with @you on the mobile scroll data — we saw the same in our research.\"", Time = "Yesterday", TimeGroup = "Yesterday",  Tab = "Mentions",  Icon = "AtSign",          IconBg = "bg-primary/10",     IconColor = "text-primary",     IsRead = true },
        new() { Id = 8,  Title = "Password changed",           Description = "Your account password was successfully changed from a trusted device.", Time = "Yesterday", TimeGroup = "Yesterday",   Tab = "Security",  Icon = "KeyRound",        IconBg = "bg-primary/10",     IconColor = "text-primary",     IsRead = true },
        new() { Id = 9,  Title = "Emma Wilson is now following you", Description = "Emma Wilson (@emma.w) started following your activity.", Time = "2 days ago",    TimeGroup = "Last 7 days",  Tab = "Followers", Icon = "UserPlus",        IconBg = "bg-primary/10",     IconColor = "text-primary",     IsRead = true },
        new() { Id = 10, Title = "Weekly summary",             Description = "Your projects received 4,280 visits and 127 new interactions this week.", Time = "3 days ago", TimeGroup = "Last 7 days", Tab = "Activity", Icon = "BarChart2",      IconBg = "bg-chart-2/20",     IconColor = "text-chart-2",     IsRead = true },
    };

    private int UnreadCount => _notifications.Count(n => !n.IsRead);

    private List<NotificationItem> VisibleNotifications => _activeTab == "All"
        ? _notifications
        : _notifications.Where(n => n.Tab == _activeTab).ToList();

    private IEnumerable<KeyValuePair<string, List<NotificationItem>>> GroupedNotifications
    {
        get
        {
            var groups = new[] { "Today", "Yesterday", "Last 7 days" };
            return groups
                .Select(g => new KeyValuePair<string, List<NotificationItem>>(
                    g,
                    VisibleNotifications.Where(n => n.TimeGroup == g).ToList()))
                .Where(kv => kv.Value.Count > 0);
        }
    }

    private int GetTabUnreadCount(string tab) => tab == "All"
        ? _notifications.Count(n => !n.IsRead)
        : _notifications.Count(n => n.Tab == tab && !n.IsRead);

    private void MarkRead(NotificationItem n) => n.IsRead = true;

    private void MarkAllRead()
    {
        foreach (var n in _notifications) n.IsRead = true;
    }

    private void ShowInfo()
        => ToastService.Info("New message", "You have a new message from the team.");

    private void ShowSuccess()
        => ToastService.Success("Changes saved", "Your preferences have been updated.");

    private void ShowWarning()
        => ToastService.Warning("Storage almost full", "You are using 85% of your quota.");

    private void ShowWithAction()
        => ToastService.Show(new ToastOptions
        {
            Title = "Team invitation",
            Description = "Alice Chen invited you to join the Design Systems team.",
            Variant = ToastVariant.Default,
            ActionLabel = "Accept",
            OnAction = () => ToastService.Success("Joined!", "You are now in the Design Systems team."),
        });

    private void ShowPersistent()
        => ToastService.Show(new ToastOptions
        {
            Title = "Background sync",
            Description = "Syncing your workspace files in the background...",
            Variant = ToastVariant.Info,
            Duration = 0,
            Dismissible = true,
        });

    private async Task ShowPromise()
    {
        await ToastService.Promise(
            action: async () =>
            {
                await Task.Delay(2000);
                return "done";
            },
            loading: new ToastOptions { Title = "Sending weekly report...", Description = "Please wait a moment." },
            success: _ => new ToastOptions { Title = "Report sent!", Description = "Your report was delivered successfully.", Variant = ToastVariant.Success },
            error: ex => new ToastOptions { Title = "Failed to send", Description = ex.Message, Variant = ToastVariant.Destructive }
        );
    }

    private string _code = @"<!-- Notifications with tabs, groups, unread indicators -->

<!-- Tabs bar -->
<Flex Class=""gap-0 border-b border-border/30"">
    @foreach (var tab in _tabs)
    {
        <button class=""@(activeTab==tab ? 'border-b-2 border-primary text-foreground' : 'text-muted-foreground hover:text-foreground')"" @onclick=""() => activeTab = tab"">
            @tab
            @if (GetTabUnreadCount(tab) > 0)
            {
                <span class=""ml-1.5 inline-flex h-4 px-1 rounded-full bg-primary text-primary-foreground text-[10px]"">@GetTabUnreadCount(tab)</span>
            }
        </button>
    }
</Flex>

<!-- Grouped notification list -->
@foreach (var group in GroupedNotifications)
{
    <Lumeo.Text Class=""text-[11px] font-semibold text-muted-foreground uppercase tracking-wide"">@group.Key</Lumeo.Text>
    @foreach (var n in group.Value)
    {
        <div class=""@(!n.IsRead ? 'bg-primary/5' : 'hover:bg-muted/50') flex items-start gap-3 rounded-lg px-3 py-3 cursor-pointer transition-colors"" @onclick=""() => MarkRead(n)"">
            <!-- Color-coded type icon -->
            <div class=""h-8 w-8 rounded-full flex items-center justify-center @n.IconBg"">
                <DynamicIcon Name=""@n.Icon"" Class=""h-4 w-4 @n.IconColor"" />
            </div>
            <Stack Class=""flex-1 min-w-0"">
                <Flex Class=""items-center gap-1.5"">
                    @if (!n.IsRead) { <div class=""h-1.5 w-1.5 rounded-full bg-primary"" /> }
                    <Lumeo.Text Class=""text-sm font-medium"">@n.Title</Lumeo.Text>
                    <Lumeo.Text As=""span"" Class=""text-[11px] text-muted-foreground ml-auto"">@n.Time</Lumeo.Text>
                </Flex>
                <Lumeo.Text Class=""text-xs text-muted-foreground"">@n.Description</Lumeo.Text>
                @if (n.ActionLabel is not null)
                {
                    <Button Variant=""Button.ButtonVariant.Outline"" Size=""Button.ButtonSize.Sm"" Class=""mt-2 h-6 text-xs w-fit"">@n.ActionLabel</Button>
                }
            </Stack>
        </div>
    }
}

<!-- Empty state -->
@if (VisibleNotifications.Count == 0)
{
    <Flex Direction=""col"" Class=""items-center py-16"">
        <div class=""h-14 w-14 rounded-full bg-muted flex items-center justify-center mb-4"">
            <DynamicIcon Name=""BellOff"" Class=""h-7 w-7 text-muted-foreground"" />
        </div>
        <Lumeo.Text Class=""text-sm font-medium"">All caught up</Lumeo.Text>
    </Flex>
}";
}
