import React, { useEffect, useState } from 'react';
import { Link, useParams } from 'react-router-dom';
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/components/ui/card';
import { cn } from '@/lib/utils';
import { Button } from '@/components/ui/button';
import { Skeleton } from '@/components/ui/skeleton';
import { Alert, AlertDescription } from '@/components/ui/alert';
import { Separator } from '@/components/ui/separator';
import {
  AchievementBadge,
  AchievementsPayload,
  FeedEntry,
  LeaderboardEntry,
  TimelinePoint,
  TopPhotoHighlight,
  TrendingEmotionHighlight,
  fetchAchievements,
} from '../services/achievementApi';
import { useGuestIdentity } from '../context/GuestIdentityContext';
import { Sparkles, Award, Trophy, Camera, Users, BarChart2, Flame } from 'lucide-react';

function formatNumber(value: number): string {
  return new Intl.NumberFormat('de-DE').format(value);
}

function formatRelativeTime(input: string): string {
  const date = new Date(input);
  if (Number.isNaN(date.getTime())) return '';
  const diff = Date.now() - date.getTime();
  const minute = 60_000;
  const hour = 60 * minute;
  const day = 24 * hour;
  if (diff < minute) return 'gerade eben';
  if (diff < hour) {
    const minutes = Math.round(diff / minute);
    return `vor ${minutes} Min`;
  }
  if (diff < day) {
    const hours = Math.round(diff / hour);
    return `vor ${hours} Std`;
  }
  const days = Math.round(diff / day);
  return `vor ${days} Tagen`;
}

function Leaderboard({ title, icon: Icon, entries, emptyCopy }: { title: string; icon: React.ElementType; entries: LeaderboardEntry[]; emptyCopy: string }) {
  return (
    <Card>
      <CardHeader className="flex flex-row items-center gap-2 pb-4">
        <div className="flex h-10 w-10 items-center justify-center rounded-full bg-pink-500/10 text-pink-500">
          <Icon className="h-5 w-5" />
        </div>
        <div>
          <CardTitle className="text-base font-semibold">{title}</CardTitle>
          <CardDescription className="text-xs">Top 5 Teilnehmer dieses Events</CardDescription>
        </div>
      </CardHeader>
      <CardContent className="space-y-2">
        {entries.length === 0 ? (
          <p className="text-sm text-muted-foreground">{emptyCopy}</p>
        ) : (
          <ol className="space-y-2 text-sm">
            {entries.map((entry, index) => (
              <li key={`${entry.guest}-${index}`} className="flex items-center justify-between rounded-lg border border-border/50 bg-muted/30 px-3 py-2">
                <div className="flex items-center gap-3">
                  <span className="text-xs font-semibold text-muted-foreground">#{index + 1}</span>
                  <span className="font-medium text-foreground">{entry.guest || 'Gast'}</span>
                </div>
                <div className="flex items-center gap-4 text-xs text-muted-foreground">
                  <span>{entry.photos} Fotos</span>
                  <span>{entry.likes} Likes</span>
                </div>
              </li>
            ))}
          </ol>
        )}
      </CardContent>
    </Card>
  );
}

function progressMeta(badge: AchievementBadge) {
  const target = badge.target ?? 0;
  const progress = badge.progress ?? 0;
  const ratio = target > 0 ? Math.min(1, progress / target) : 0;
  return {
    progress,
    target,
    ratio: badge.earned ? 1 : ratio,
  };
}

function BadgesGrid({ badges }: { badges: AchievementBadge[] }) {
  if (badges.length === 0) {
    return (
      <Card>
        <CardHeader>
          <CardTitle>Badges</CardTitle>
          <CardDescription>Erfülle Aufgaben und sammle Likes, um Badges freizuschalten.</CardDescription>
        </CardHeader>
        <CardContent>
          <p className="text-sm text-muted-foreground">Noch keine Badges verfügbar.</p>
        </CardContent>
      </Card>
    );
  }

  return (
    <Card>
      <CardHeader>
        <CardTitle>Badges</CardTitle>
        <CardDescription>Dein Fortschritt bei den verfügbaren Erfolgen.</CardDescription>
      </CardHeader>
      <CardContent className="grid grid-cols-2 gap-3 sm:grid-cols-3">
        {badges.map((badge) => {
          const { ratio } = progressMeta(badge);
          const percentage = Math.round(ratio * 100);
          return (
            <div
              key={badge.id}
              className={cn(
                'relative overflow-hidden rounded-2xl border px-4 py-3 shadow-sm transition',
                badge.earned
                  ? 'border-emerald-400/40 bg-gradient-to-br from-emerald-500/20 via-emerald-500/5 to-white text-emerald-900'
                  : 'border-border/60 bg-white/80',
              )}
            >
              <div className="flex items-start justify-between gap-2">
                <div>
                  <p className="text-sm font-semibold text-foreground">{badge.title}</p>
                  <p className="text-xs text-muted-foreground line-clamp-2">{badge.description}</p>
                </div>
                <span className="rounded-full bg-white/30 p-2 text-pink-500">
                  <Award className="h-4 w-4" />
                </span>
              </div>
              <div className="mt-3">
                <div className="h-2 w-full overflow-hidden rounded-full bg-muted/40">
                  <div
                    className={cn('h-2 rounded-full transition-all', badge.earned ? 'bg-emerald-500' : 'bg-pink-500')}
                    style={{ width: `${Math.max(8, percentage)}%` }}
                  />
                </div>
                <p className="mt-1 text-xs text-muted-foreground">
                  {badge.earned ? 'Freigeschaltet 🎉' : `Fortschritt: ${badge.progress}/${badge.target}`}
                </p>
              </div>
            </div>
          );
        })}
      </CardContent>
    </Card>
  );
}

function Timeline({ points }: { points: TimelinePoint[] }) {
  if (points.length === 0) {
    return null;
  }
  return (
    <Card>
      <CardHeader>
        <CardTitle>Timeline</CardTitle>
        <CardDescription>Wie das Event im Laufe der Zeit Fahrt aufgenommen hat.</CardDescription>
      </CardHeader>
      <CardContent className="space-y-2 text-sm">
        {points.map((point) => (
          <div key={point.date} className="flex items-center justify-between rounded-lg border border-border/40 bg-muted/20 px-3 py-2">
            <span className="font-medium text-foreground">{point.date}</span>
            <span className="text-muted-foreground">{point.photos} Fotos | {point.guests} Gäste</span>
          </div>
        ))}
      </CardContent>
    </Card>
  );
}

function Feed({ feed }: { feed: FeedEntry[] }) {
  if (feed.length === 0) {
    return (
      <Card>
        <CardHeader>
          <CardTitle>Live Feed</CardTitle>
          <CardDescription>Neue Uploads erscheinen hier in Echtzeit.</CardDescription>
        </CardHeader>
        <CardContent>
          <p className="text-sm text-muted-foreground">Noch keine Uploads – starte die Kamera und lege los!</p>
        </CardContent>
      </Card>
    );
  }

  return (
    <Card>
      <CardHeader>
        <CardTitle>Live Feed</CardTitle>
        <CardDescription>Die neuesten Momente aus deinem Event.</CardDescription>
      </CardHeader>
      <CardContent className="space-y-3">
        {feed.map((item) => (
          <div key={item.photoId} className="flex items-center gap-3 rounded-lg border border-border/40 bg-muted/20 p-3">
            {item.thumbnail ? (
              <img src={item.thumbnail} alt="Vorschau" className="h-16 w-16 rounded-md object-cover" />
            ) : (
              <div className="flex h-16 w-16 items-center justify-center rounded-md bg-muted"> <Camera className="h-6 w-6 text-muted-foreground" /> </div>
            )}
            <div className="flex-1 text-sm">
              <p className="font-semibold text-foreground">{item.guest || 'Gast'}</p>
              {item.task && <p className="text-xs text-muted-foreground">Aufgabe: {item.task}</p>}
              <div className="mt-1 flex items-center gap-4 text-xs text-muted-foreground">
                <span>{formatRelativeTime(item.createdAt)}</span>
                <span>{item.likes} Likes</span>
              </div>
            </div>
          </div>
        ))}
      </CardContent>
    </Card>
  );
}

function Highlights({ topPhoto, trendingEmotion }: { topPhoto: TopPhotoHighlight | null; trendingEmotion: TrendingEmotionHighlight | null }) {
  if (!topPhoto && !trendingEmotion) {
    return null;
  }

  return (
    <div className="grid gap-4 md:grid-cols-2">
      {topPhoto && (
        <Card>
          <CardHeader className="flex flex-row items-center justify-between">
            <div>
              <CardTitle>Publikumsliebling</CardTitle>
              <CardDescription>Das Foto mit den meisten Likes.</CardDescription>
            </div>
            <Trophy className="h-6 w-6 text-amber-400" />
          </CardHeader>
          <CardContent className="space-y-2 text-sm">
            <div className="overflow-hidden rounded-xl border border-border/40">
              {topPhoto.thumbnail ? (
                <img src={topPhoto.thumbnail} alt="Top Foto" className="h-48 w-full object-cover" />
              ) : (
                <div className="flex h-48 w-full items-center justify-center bg-muted text-muted-foreground">Kein Vorschau-Bild</div>
              )}
            </div>
            <p><span className="font-semibold text-foreground">{topPhoto.guest || 'Gast'}</span> – {topPhoto.likes} Likes</p>
            {topPhoto.task && <p className="text-muted-foreground">Aufgabe: {topPhoto.task}</p>}
            <p className="text-xs text-muted-foreground">{formatRelativeTime(topPhoto.createdAt)}</p>
          </CardContent>
        </Card>
      )}

      {trendingEmotion && (
        <Card>
          <CardHeader className="flex flex-row items-center justify-between">
            <div>
              <CardTitle>Trend-Emotion</CardTitle>
              <CardDescription>Diese Stimmung taucht gerade besonders oft auf.</CardDescription>
            </div>
            <Flame className="h-6 w-6 text-pink-500" />
          </CardHeader>
          <CardContent>
            <p className="text-lg font-semibold text-foreground">{trendingEmotion.name}</p>
            <p className="text-sm text-muted-foreground">{trendingEmotion.count} Fotos mit dieser Stimmung</p>
          </CardContent>
        </Card>
      )}
    </div>
  );
}

function FlowSummary({ data, token }: { data: AchievementsPayload; token: string }) {
  const personal = data.personal;
  const tasksDone = personal?.tasks ?? data.summary.tasksSolved;
  const photos = personal?.photos ?? data.summary.totalPhotos;
  const likes = personal?.likes ?? data.summary.likesTotal;
  const guests = data.summary.uniqueGuests;
  const earnedBadges = personal?.badges.filter((badge) => badge.earned).length ?? 0;
  const nextBadge = personal?.badges.find((badge) => !badge.earned);

  return (
    <section className="rounded-[32px] border border-slate-100 bg-white/95 p-6 shadow-sm dark:border-white/10 dark:bg-slate-900/70">
      <div className="flex flex-wrap items-center justify-between gap-4">
        <div>
          <p className="text-xs uppercase tracking-[0.35em] text-slate-500 dark:text-white/60">Dein Flow</p>
          <h2 className="mt-1 text-2xl font-semibold text-slate-900 dark:text-white">
            {tasksDone === 0 ? 'Starte deine erste Mission.' : 'Weiter so, dein Event lebt!'}
          </h2>
          <p className="text-sm text-slate-500 dark:text-white/70">
            {nextBadge ? `Noch ${Math.max(0, nextBadge.target - nextBadge.progress)} Schritte bis „${nextBadge.title}“.` : 'Alle aktuellen Badges freigeschaltet.'}
          </p>
        </div>
        <div className="flex gap-2">
          <Button asChild>
            <Link to={`/e/${encodeURIComponent(token)}/tasks`} className="flex items-center gap-2">
              <Sparkles className="h-4 w-4" />
              Aufgabe ziehen
            </Link>
          </Button>
          <Button variant="outline" asChild>
            <Link to={`/e/${encodeURIComponent(token)}/gallery`} className="flex items-center gap-2">
              <Camera className="h-4 w-4" />
              Galerie öffnen
            </Link>
          </Button>
        </div>
      </div>
      <div className="mt-4 grid gap-3 sm:grid-cols-2 lg:grid-cols-4">
        <FlowStat label="Deine Aufgaben" value={formatNumber(tasksDone)} />
        <FlowStat label="Fotos gesamt" value={formatNumber(photos)} />
        <FlowStat label="Likes gesammelt" value={formatNumber(likes)} />
        <FlowStat label="Badges" value={`${earnedBadges}/${personal?.badges.length ?? 0}`} />
      </div>
      <div className="mt-4 grid gap-3 sm:grid-cols-2">
        <FlowStat label="Aktive Gäste" value={formatNumber(guests)} />
        <FlowStat label="Letzte Mission" value={personal ? personal.guestName || 'Gast' : 'Event'} muted />
      </div>
    </section>
  );
}

function FlowStat({ label, value, muted = false }: { label: string; value: string; muted?: boolean }) {
  return (
    <div
      className={cn(
        'rounded-2xl border border-slate-100 bg-white/80 px-4 py-3 text-left shadow-sm dark:border-white/10 dark:bg-white/5',
        muted && 'opacity-80'
      )}
    >
      <p className="text-[0.65rem] uppercase tracking-[0.35em] text-slate-400 dark:text-white/60">{label}</p>
      <p className="mt-2 text-xl font-semibold text-slate-900 dark:text-white">{value}</p>
    </div>
  );
}

function PersonalActions({ token }: { token: string }) {
  return (
    <div className="flex flex-wrap gap-3">
      <Button asChild>
        <Link to={`/e/${encodeURIComponent(token)}/upload`} className="flex items-center gap-2">
          <Camera className="h-4 w-4" />
          Neues Foto hochladen
        </Link>
      </Button>
      <Button variant="outline" asChild>
        <Link to={`/e/${encodeURIComponent(token)}/tasks`} className="flex items-center gap-2">
          <Sparkles className="h-4 w-4" />
          Aufgabe ziehen
        </Link>
      </Button>
    </div>
  );
}

export default function AchievementsPage() {
  const { token } = useParams<{ token: string }>();
  const identity = useGuestIdentity();
  const [data, setData] = useState<AchievementsPayload | null>(null);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState<string | null>(null);
  const [activeTab, setActiveTab] = useState<'personal' | 'event' | 'feed'>('personal');

  const personalName = identity.hydrated && identity.name ? identity.name : undefined;

  useEffect(() => {
    if (!token) return;
    const controller = new AbortController();
    setLoading(true);
    setError(null);

    fetchAchievements(token, personalName, controller.signal)
      .then((payload) => {
        setData(payload);
        if (!payload.personal) {
          setActiveTab('event');
        }
      })
      .catch((err) => {
        if (err.name === 'AbortError') return;
        console.error('Failed to load achievements', err);
        setError(err.message || 'Erfolge konnten nicht geladen werden.');
      })
      .finally(() => setLoading(false));

    return () => controller.abort();
  }, [token, personalName]);

  const hasPersonal = Boolean(data?.personal);

  if (!token) {
    return null;
  }

  return (
    <div className="space-y-6 pb-24">
      <div className="space-y-2">
        <div className="flex items-center gap-3">
          <div className="flex h-10 w-10 items-center justify-center rounded-full bg-pink-500/10 text-pink-500">
            <Award className="h-5 w-5" />
          </div>
          <div>
            <h1 className="text-2xl font-semibold text-foreground">Erfolge</h1>
            <p className="text-sm text-muted-foreground">Behalte deine Highlights, Badges und die aktivsten Gäste im Blick.</p>
          </div>
        </div>
      </div>

      {loading && (
        <div className="space-y-4">
          <Skeleton className="h-24 w-full" />
          <Skeleton className="h-32 w-full" />
          <Skeleton className="h-48 w-full" />
        </div>
      )}

      {!loading && error && (
        <Alert variant="destructive">
          <AlertDescription className="flex items-center justify-between gap-3">
            <span>{error}</span>
            <Button variant="outline" size="sm" onClick={() => setActiveTab(hasPersonal ? 'personal' : 'event')}>
              Erneut versuchen
            </Button>
          </AlertDescription>
        </Alert>
      )}

      {!loading && !error && data && (
        <>
          <FlowSummary data={data} token={token} />

          <div className="flex flex-wrap items-center gap-2">
            <Button
              variant={activeTab === 'personal' ? 'default' : 'outline'}
              onClick={() => setActiveTab('personal')}
              disabled={!hasPersonal}
              className="flex items-center gap-2"
            >
              <Sparkles className="h-4 w-4" />
              Meine Erfolge
            </Button>
            <Button
              variant={activeTab === 'event' ? 'default' : 'outline'}
              onClick={() => setActiveTab('event')}
              className="flex items-center gap-2"
            >
              <Users className="h-4 w-4" />
              Event Highlights
            </Button>
            <Button
              variant={activeTab === 'feed' ? 'default' : 'outline'}
              onClick={() => setActiveTab('feed')}
              className="flex items-center gap-2"
            >
              <BarChart2 className="h-4 w-4" />
              Live Feed
            </Button>
          </div>

          <Separator />

          {activeTab === 'personal' && hasPersonal && data.personal && (
            <div className="space-y-5">
              <Card>
                <CardHeader className="flex flex-col gap-3 sm:flex-row sm:items-center sm:justify-between">
                  <div>
                    <CardTitle className="text-lg font-semibold">Hi {data.personal.guestName || identity.name || 'Gast'}!</CardTitle>
                    <CardDescription>
                      {data.personal.photos} Fotos | {data.personal.tasks} Aufgaben | {data.personal.likes} Likes
                    </CardDescription>
                  </div>
                  <PersonalActions token={token} />
                </CardHeader>
              </Card>

              <BadgesGrid badges={data.personal.badges} />
            </div>
          )}

          {activeTab === 'event' && (
            <div className="space-y-5">
              <Highlights topPhoto={data.highlights.topPhoto} trendingEmotion={data.highlights.trendingEmotion} />
              <Timeline points={data.highlights.timeline} />
              <div className="grid gap-4 lg:grid-cols-2">
                <Leaderboard
                  title="Top Uploads"
                  icon={Users}
                  entries={data.leaderboards.uploads}
                  emptyCopy="Noch keine Uploads – sobald Fotos vorhanden sind, erscheinen sie hier."
                />
                <Leaderboard
                  title="Beliebteste Gäste"
                  icon={Trophy}
                  entries={data.leaderboards.likes}
                  emptyCopy="Likes fehlen noch – motiviere die Gäste, Fotos zu liken."
                />
              </div>
            </div>
          )}

          {activeTab === 'feed' && <Feed feed={data.feed} />}
        </>
      )}
    </div>
  );
}
