'use client';

import { useEffect, useState } from 'react';
import { useRouter } from 'next/navigation';
import { ArrowLeft, Save, Plus, X } from 'lucide-react';
import Link from 'next/link';
import toast from 'react-hot-toast';
import api from '@/lib/api';
import { LocalizedString, MediaItem } from '@/types';
import Button from '@/components/ui/Button';
import Input, { Textarea } from '@/components/ui/Input';
import ImageUploader from '@/components/ui/ImageUploader';
import MediaUploader from '@/components/ui/MediaUploader';
import { PageSpinner } from '@/components/ui/Spinner';
import LanguageTabs, { useLanguageTabs, Lang } from '@/components/ui/LanguageTabs';
import Section from '@/components/ui/Section';

const emptyLS = (): LocalizedString => ({ en: '', zh: '' });

function asLS(val: unknown): LocalizedString {
  if (val && typeof val === 'object' && 'en' in val) return val as LocalizedString;
  if (typeof val === 'string') return { en: val, zh: '' };
  return emptyLS();
}

export default function EventGalleryEditorClient({ id }: { id: string }) {
  const router = useRouter();
  const isNew = id === 'new';
  const { activeLang, setActiveLang } = useLanguageTabs();

  const [isLoading, setIsLoading] = useState(!isNew);
  const [isSaving, setIsSaving] = useState(false);

  const [title, setTitle] = useState<LocalizedString>(emptyLS());
  const [description, setDescription] = useState<LocalizedString>(emptyLS());
  const [coverImage, setCoverImage] = useState('');
  const [media, setMedia] = useState<MediaItem[]>([]);
  const [eventDate, setEventDate] = useState(new Date().toISOString().split('T')[0]);
  const [status, setStatus] = useState<'draft' | 'published'>('draft');
  const [cardSize, setCardSize] = useState<'small' | 'wide' | 'tall' | 'large'>('small');
  const [order, setOrder] = useState(0);

  const updateLS = (setter: React.Dispatch<React.SetStateAction<LocalizedString>>, lang: Lang, value: string) => {
    setter((prev) => ({ ...prev, [lang]: value }));
  };

  useEffect(() => {
    if (isNew) return;
    api
      .getEventGalleryItem(id)
      .then((data) => {
        setTitle(asLS(data.title));
        setDescription(asLS(data.description));
        setCoverImage(data.coverImage ?? '');
        const loadedMedia = data.media?.length
          ? data.media
          : (data.photos ?? []).map((url: string) => ({ url, type: 'image' as const }));
        setMedia(loadedMedia);
        setEventDate(data.eventDate ? new Date(data.eventDate).toISOString().split('T')[0] : '');
        setStatus(data.status ?? 'draft');
        setCardSize(data.cardSize ?? 'small');
        setOrder(data.order ?? 0);
      })
      .catch(() => {
        toast.error('Failed to load event');
        router.push('/event-gallery');
      })
      .finally(() => setIsLoading(false));
  }, [id, isNew, router]);

  const handleSave = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!title.en && !title.zh) {
      toast.error('Title is required');
      return;
    }
    setIsSaving(true);
    try {
      const payload = {
        title,
        description,
        coverImage: coverImage || undefined,
        media: media.filter(m => m.url),
        eventDate,
        status,
        cardSize,
        order,
      };
      if (isNew) {
        await api.createEventGalleryItem(payload);
        toast.success('Event created');
      } else {
        await api.updateEventGalleryItem(id, payload);
        toast.success('Event updated');
      }
      router.push('/event-gallery');
    } catch (err) {
      toast.error(err instanceof Error ? err.message : 'Failed to save');
    } finally {
      setIsSaving(false);
    }
  };

  const addMediaSlot = () => setMedia([...media, { url: '', type: 'image' }]);
  const removeMediaItem = (idx: number) => setMedia(media.filter((_, i) => i !== idx));
  const updateMediaItem = (idx: number, item: MediaItem | null) => {
    if (!item) { removeMediaItem(idx); return; }
    setMedia(media.map((m, i) => (i === idx ? item : m)));
  };

  if (isLoading) return <PageSpinner />;

  return (
    <div className="space-y-5">
      <div className="flex items-center justify-between">
        <div className="flex items-center gap-3">
          <Link href="/event-gallery" className="p-2 text-gray-400 hover:text-gray-600 hover:bg-gray-100 rounded-lg transition-colors">
            <ArrowLeft size={20} />
          </Link>
          <h1 className="text-2xl font-bold text-gray-900">
            {isNew ? 'New Event' : 'Edit Event'}
          </h1>
        </div>
        <Button type="submit" form="event-form" isLoading={isSaving}>
          <Save size={16} />
          {isNew ? 'Create' : 'Save changes'}
        </Button>
      </div>

      <form id="event-form" onSubmit={handleSave} className="space-y-5">
        <LanguageTabs activeLang={activeLang} onChange={setActiveLang} />

        <div className="grid grid-cols-1 lg:grid-cols-3 gap-5">
          <div className="lg:col-span-2 space-y-5">
            <Section title="Event Details">
              <Input
                label={`Title (${activeLang.toUpperCase()})`}
                value={title[activeLang]}
                onChange={(e) => updateLS(setTitle, activeLang, e.target.value)}
                required
              />
              <Textarea
                label={`Description (${activeLang.toUpperCase()})`}
                value={description[activeLang]}
                onChange={(e) => updateLS(setDescription, activeLang, e.target.value)}
                rows={3}
              />
            </Section>

            <Section title="Media Gallery">
              <p className="text-xs text-gray-500">Upload photos and videos for this event. They will be displayed in a masonry layout on the event detail page.</p>
              <div className="grid grid-cols-2 md:grid-cols-3 gap-4">
                {media.map((item, idx) => (
                  <div key={idx} className="relative">
                    <MediaUploader
                      label={`${item.type === 'video' ? 'Video' : 'Photo'} ${idx + 1}`}
                      value={item.url ? item : null}
                      onChange={(val) => updateMediaItem(idx, val)}
                      previewHeight="h-32"
                    />
                    <button
                      type="button"
                      onClick={() => removeMediaItem(idx)}
                      className="absolute top-0 right-0 p-1 bg-red-500 text-white rounded-bl-lg rounded-tr-lg hover:bg-red-600 z-10"
                    >
                      <X size={14} />
                    </button>
                  </div>
                ))}
              </div>
              <Button type="button" variant="secondary" size="sm" onClick={addMediaSlot}>
                <Plus size={14} />
                Add photo / video
              </Button>
            </Section>
          </div>

          <div className="space-y-5">
            <Section title="Cover Image">
              <ImageUploader label="Cover / Thumbnail" value={coverImage} onChange={setCoverImage} />
            </Section>

            <Section title="Publishing">
              <div className="space-y-3">
                <div>
                  <label className="block text-sm font-medium text-gray-700 mb-1">Status</label>
                  <select
                    value={status}
                    onChange={(e) => setStatus(e.target.value as 'draft' | 'published')}
                    className="w-full px-3 py-2 text-sm border border-gray-300 rounded-lg focus:outline-none focus:ring-2 focus:ring-blue-500"
                  >
                    <option value="draft">Draft</option>
                    <option value="published">Published</option>
                  </select>
                </div>
                <div>
                  <label className="block text-sm font-medium text-gray-700 mb-1">Card Size</label>
                  <select
                    value={cardSize}
                    onChange={(e) => setCardSize(e.target.value as 'small' | 'wide' | 'tall' | 'large')}
                    className="w-full px-3 py-2 text-sm border border-gray-300 rounded-lg focus:outline-none focus:ring-2 focus:ring-blue-500"
                  >
                    <option value="small">Regular (1×1)</option>
                    <option value="wide">Wide (2×1)</option>
                    <option value="tall">Tall (1×2)</option>
                    <option value="large">Featured (2×2)</option>
                  </select>
                  <p className="mt-1 text-xs text-gray-400">Controls the card footprint on the gallery grid (columns × rows)</p>
                </div>
                <Input
                  label="Event Date"
                  type="date"
                  value={eventDate}
                  onChange={(e) => setEventDate(e.target.value)}
                />
                <Input
                  label="Sort Order"
                  type="number"
                  value={order.toString()}
                  onChange={(e) => setOrder(parseInt(e.target.value) || 0)}
                />
              </div>
            </Section>
          </div>
        </div>
      </form>
    </div>
  );
}
