import { useState, useEffect, useCallback } from "react";
import type { Calendar, CalendarSubscription } from "../types";
import { api } from "../api";
import Modal from "./Modal";

const COLORS = [
  "#3B82F6", "#EF4444", "#10B981", "#F59E0B", "#8B5CF6",
  "#EC4899", "#06B6D4", "#F97316", "#6366F1", "#14B8A6",
  "#84CC16", "#A855F7",
];

interface CalendarModalProps {
  open: boolean;
  onClose: () => void;
  onSaved: () => void;
  calendar?: Calendar | null;
}

function copyToClipboard(text: string) {
  navigator.clipboard.writeText(text);
}

export default function CalendarModal({
  open,
  onClose,
  onSaved,
  calendar,
}: CalendarModalProps) {
  const isEdit = !!calendar;

  const [name, setName] = useState("");
  const [color, setColor] = useState(COLORS[0]);
  const [countForAvailability, setCountForAvailability] = useState(true);
  const [defaultReminderMinutes, setDefaultReminderMinutes] = useState<number | "">(10);
  const [sortOrder, setSortOrder] = useState<number | "">(0);
  const [saving, setSaving] = useState(false);
  const [error, setError] = useState("");
  const [showDelete, setShowDelete] = useState(false);
  const [subscriptions, setSubscriptions] = useState<CalendarSubscription[]>([]);
  const [subsLoading, setSubsLoading] = useState(false);
  const [addSubUrl, setAddSubUrl] = useState("");
  const [addSubSaving, setAddSubSaving] = useState(false);
  const [syncingId, setSyncingId] = useState<string | null>(null);
  const [copiedUrl, setCopiedUrl] = useState(false);

  const loadSubscriptions = useCallback(async () => {
    if (!calendar?.id) return;
    setSubsLoading(true);
    try {
      const res = await api.listSubscriptions(calendar.id);
      setSubscriptions(res.items || []);
    } catch {
      setSubscriptions([]);
    } finally {
      setSubsLoading(false);
    }
  }, [calendar?.id]);

  useEffect(() => {
    if (!open) return;
    setError("");
    setShowDelete(false);
    setAddSubUrl("");
    if (calendar) {
      setName(calendar.name);
      setColor(calendar.color);
      setCountForAvailability(calendar.count_for_availability ?? true);
      setDefaultReminderMinutes(calendar.default_reminder_minutes ?? 10);
      setSortOrder(calendar.sort_order ?? 0);
      loadSubscriptions();
    } else {
      setName("");
      setColor(COLORS[Math.floor(Math.random() * COLORS.length)]);
      setCountForAvailability(true);
      setDefaultReminderMinutes(10);
      setSortOrder(0);
      setSubscriptions([]);
    }
  }, [open, calendar, loadSubscriptions]);

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!name.trim()) return;
    setSaving(true);
    setError("");
    try {
      if (isEdit) {
        await api.updateCalendar(calendar!.id, {
          name: name.trim(),
          color,
          count_for_availability: countForAvailability,
          default_reminder_minutes: defaultReminderMinutes === "" ? undefined : defaultReminderMinutes,
          sort_order: sortOrder === "" ? undefined : sortOrder,
        });
      } else {
        await api.createCalendar({ name: name.trim(), color });
      }
      onSaved();
      onClose();
    } catch (err: any) {
      setError(err.error || "Failed to save calendar");
    } finally {
      setSaving(false);
    }
  };

  const handleDelete = async () => {
    if (!calendar) return;
    setSaving(true);
    try {
      await api.deleteCalendar(calendar.id);
      onSaved();
      onClose();
    } catch (err: any) {
      setError(err.error || "Failed to delete calendar");
    } finally {
      setSaving(false);
    }
  };

  const handleAddSubscription = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!calendar?.id || !addSubUrl.trim()) return;
    setAddSubSaving(true);
    try {
      await api.addSubscription(calendar.id, { url: addSubUrl.trim() });
      setAddSubUrl("");
      loadSubscriptions();
      onSaved();
    } catch (err: any) {
      setError(err.error || "Failed to add subscription");
    } finally {
      setAddSubSaving(false);
    }
  };

  const handleDeleteSubscription = async (subId: string) => {
    if (!calendar?.id) return;
    try {
      await api.deleteSubscription(calendar.id, subId);
      loadSubscriptions();
      onSaved();
    } catch (err: any) {
      setError(err.error || "Failed to remove subscription");
    }
  };

  const handleSyncSubscription = async (subId: string) => {
    if (!calendar?.id) return;
    setSyncingId(subId);
    try {
      await api.syncSubscription(calendar.id, subId);
      loadSubscriptions();
      onSaved();
    } catch (err: any) {
      setError(err.error || "Failed to sync");
    } finally {
      setSyncingId(null);
    }
  };

  const handleCopyUrl = (url: string) => {
    copyToClipboard(url);
    setCopiedUrl(true);
    setTimeout(() => setCopiedUrl(false), 1500);
  };

  return (
    <Modal
      open={open}
      onClose={onClose}
      title={isEdit ? "Edit Calendar" : "New Calendar"}
    >
      <form onSubmit={handleSubmit} className="space-y-5">
        {error && (
          <div className="text-sm text-red-600 dark:text-red-400 bg-red-50 dark:bg-red-900/20 px-3 py-2 rounded-lg">
            {error}
          </div>
        )}

        <div>
          <input
            type="text"
            placeholder="Calendar name"
            value={name}
            onChange={(e) => setName(e.target.value)}
            className="w-full text-lg font-medium bg-transparent border-0 border-b-2 border-gray-200 dark:border-gray-600 focus:border-blue-500 dark:focus:border-blue-400 focus:ring-0 px-0 py-2 text-gray-900 dark:text-white placeholder-gray-400 outline-none transition-colors"
            autoFocus
            required
            maxLength={80}
          />
        </div>

        <div>
          <label className="block text-xs font-medium text-gray-500 dark:text-gray-400 mb-2">
            Color
          </label>
          <div className="flex flex-wrap gap-2">
            {COLORS.map((c) => (
              <button
                key={c}
                type="button"
                onClick={() => setColor(c)}
                className={`w-8 h-8 rounded-full transition-all ${
                  color === c
                    ? "ring-2 ring-offset-2 ring-offset-white dark:ring-offset-gray-800 scale-110"
                    : "hover:scale-110"
                }`}
                style={{ backgroundColor: c, outlineColor: color === c ? c : undefined }}
              />
            ))}
          </div>
        </div>

        {isEdit && (
          <>
            <div className="flex items-center gap-2">
              <input
                type="checkbox"
                id="count_for_availability"
                checked={countForAvailability}
                onChange={(e) => setCountForAvailability(e.target.checked)}
                className="rounded border-gray-300 dark:border-gray-600 text-blue-600 focus:ring-blue-500"
              />
              <label
                htmlFor="count_for_availability"
                className="text-sm text-gray-700 dark:text-gray-300"
              >
                Include in availability / Count as busy
              </label>
            </div>

            {calendar?.availability_url && (
              <div>
                <label className="block text-xs font-medium text-gray-500 dark:text-gray-400 mb-1">
                  Availability URL
                </label>
                <div className="flex gap-2">
                  <input
                    type="text"
                    readOnly
                    value={calendar.availability_url}
                    className="flex-1 px-3 py-2 rounded-lg border border-gray-200 dark:border-gray-600 bg-gray-50 dark:bg-gray-800 text-sm text-gray-600 dark:text-gray-400 truncate"
                  />
                  <button
                    type="button"
                    onClick={() => handleCopyUrl(calendar.availability_url!)}
                    className="px-3 py-2 text-sm text-blue-600 dark:text-blue-400 hover:bg-blue-50 dark:hover:bg-blue-900/20 rounded-lg transition-colors"
                  >
                    {copiedUrl ? "Copied!" : "Copy"}
                  </button>
                </div>
                <p className="text-xs text-gray-500 dark:text-gray-400 mt-1">
                  Share with Calendly, Cal.com, etc. to block busy times
                </p>
              </div>
            )}

            <div className="grid grid-cols-2 gap-4">
              <div>
                <label className="block text-xs font-medium text-gray-500 dark:text-gray-400 mb-1">
                  Default reminder (min)
                </label>
                <input
                  type="number"
                  min={0}
                  max={10080}
                  value={defaultReminderMinutes}
                  onChange={(e) =>
                    setDefaultReminderMinutes(
                      e.target.value === "" ? "" : parseInt(e.target.value, 10) || 0,
                    )
                  }
                  className="w-full px-3 py-2 rounded-lg border border-gray-200 dark:border-gray-600 bg-gray-50 dark:bg-gray-700 text-sm text-gray-900 dark:text-white focus:ring-2 focus:ring-blue-500 outline-none"
                />
              </div>
              <div>
                <label className="block text-xs font-medium text-gray-500 dark:text-gray-400 mb-1">
                  Sort order
                </label>
                <input
                  type="number"
                  value={sortOrder}
                  onChange={(e) =>
                    setSortOrder(
                      e.target.value === "" ? "" : parseInt(e.target.value, 10) || 0,
                    )
                  }
                  className="w-full px-3 py-2 rounded-lg border border-gray-200 dark:border-gray-600 bg-gray-50 dark:bg-gray-700 text-sm text-gray-900 dark:text-white focus:ring-2 focus:ring-blue-500 outline-none"
                />
              </div>
            </div>

            {calendar?.role === "owner" || calendar?.role === "editor" ? (
              <div>
                <label className="block text-xs font-medium text-gray-500 dark:text-gray-400 mb-2">
                  Subscribed URLs
                </label>
                {subsLoading ? (
                  <p className="text-sm text-gray-500 dark:text-gray-400">Loading...</p>
                ) : subscriptions.length === 0 ? (
                  <p className="text-sm text-gray-500 dark:text-gray-400">
                    No subscriptions. Add a URL to import events from an external calendar.
                  </p>
                ) : (
                  <ul className="space-y-2 mb-2">
                    {subscriptions.map((sub) => (
                      <li
                        key={sub.id}
                        className="flex items-center justify-between gap-2 p-2 rounded-lg bg-gray-50 dark:bg-gray-800 text-sm"
                      >
                        <span className="truncate text-gray-700 dark:text-gray-300" title={sub.source_url}>
                          {sub.source_url}
                        </span>
                        <div className="flex gap-1 flex-shrink-0">
                          <button
                            type="button"
                            onClick={() => handleSyncSubscription(sub.id)}
                            disabled={syncingId === sub.id}
                            className="px-2 py-1 text-xs text-blue-600 dark:text-blue-400 hover:bg-blue-50 dark:hover:bg-blue-900/20 rounded transition-colors disabled:opacity-50"
                          >
                            {syncingId === sub.id ? "Syncing..." : "Sync"}
                          </button>
                          <button
                            type="button"
                            onClick={() => handleDeleteSubscription(sub.id)}
                            className="px-2 py-1 text-xs text-red-500 hover:bg-red-50 dark:hover:bg-red-900/20 rounded transition-colors"
                          >
                            Remove
                          </button>
                        </div>
                      </li>
                    ))}
                  </ul>
                )}
                <div className="flex gap-2">
                  <input
                    type="url"
                    placeholder="https://... or webcal://..."
                    value={addSubUrl}
                    onChange={(e) => setAddSubUrl(e.target.value)}
                    onKeyDown={(e) => {
                      if (e.key === "Enter") {
                        e.preventDefault();
                        handleAddSubscription(e as unknown as React.FormEvent);
                      }
                    }}
                    className="flex-1 px-3 py-2 rounded-lg border border-gray-200 dark:border-gray-600 bg-gray-50 dark:bg-gray-700 text-sm text-gray-900 dark:text-white focus:ring-2 focus:ring-blue-500 outline-none placeholder-gray-400"
                  />
                  <button
                    type="button"
                    onClick={handleAddSubscription}
                    disabled={addSubSaving || !addSubUrl.trim()}
                    className="px-3 py-2 text-sm text-blue-600 dark:text-blue-400 hover:bg-blue-50 dark:hover:bg-blue-900/20 rounded-lg transition-colors font-medium disabled:opacity-50"
                  >
                    {addSubSaving ? "Adding..." : "Add"}
                  </button>
                </div>
              </div>
            ) : null}
          </>
        )}

        <div className="flex items-center justify-between pt-2">
          <div>
            {isEdit && calendar?.role === "owner" && !showDelete && (
              <button
                type="button"
                onClick={() => setShowDelete(true)}
                className="text-sm text-red-500 hover:text-red-700 dark:hover:text-red-400 transition-colors"
              >
                Delete calendar
              </button>
            )}
            {isEdit && showDelete && (
              <div className="flex items-center gap-2">
                <span className="text-sm text-red-500">Delete?</span>
                <button
                  type="button"
                  onClick={handleDelete}
                  className="text-sm text-white bg-red-500 hover:bg-red-600 px-3 py-1 rounded-lg transition-colors"
                  disabled={saving}
                >
                  Yes
                </button>
                <button
                  type="button"
                  onClick={() => setShowDelete(false)}
                  className="text-sm text-gray-500 hover:text-gray-700 dark:text-gray-400 transition-colors"
                >
                  No
                </button>
              </div>
            )}
          </div>
          <div className="flex gap-2">
            <button
              type="button"
              onClick={onClose}
              className="px-4 py-2 text-sm text-gray-700 dark:text-gray-300 hover:bg-gray-100 dark:hover:bg-gray-700 rounded-lg transition-colors"
            >
              Cancel
            </button>
            <button
              type="submit"
              disabled={saving || !name.trim()}
              className="px-4 py-2 text-sm text-white bg-blue-600 hover:bg-blue-700 disabled:opacity-50 rounded-lg transition-colors font-medium"
            >
              {saving ? "Saving..." : isEdit ? "Update" : "Create"}
            </button>
          </div>
        </div>
      </form>
    </Modal>
  );
}
