"use client";

import { useState, useEffect, useRef, useId } from "react";
import * as Dialog from "@radix-ui/react-dialog";
import { motion, AnimatePresence } from "framer-motion";
import {
  X,
  Loader2,
  CheckCircle2,
  Phone,
  User,
  Mail,
  MapPin,
  MessageSquare,
  Car,
} from "lucide-react";
import { submitLead, trackLeadClick } from "@/lib/api";
import { cn } from "@/lib/utils";

// ─── Types ────────────────────────────────────────────────────────────────────

interface OnRoadPriceModalProps {
  car: { id: string; name: string; variants?: Array<{ name: string }> };
  isOpen: boolean;
  onClose: () => void;
  selectedVariant?: string;
}

interface FormState {
  name: string;
  mobile: string;
  email: string;
  pinCode: string;
  city: string;
  state: string;
  variant: string;
  message: string;
}

interface FormErrors {
  name?: string;
  mobile?: string;
  city?: string;
  pinCode?: string;
}

// ─── Validation ───────────────────────────────────────────────────────────────

function validate(form: FormState): FormErrors {
  const errors: FormErrors = {};
  if (!form.name.trim()) errors.name = "Full name is required";
  if (!form.mobile.trim()) {
    errors.mobile = "Mobile number is required";
  } else if (!/^\d{10}$/.test(form.mobile.trim())) {
    errors.mobile = "Enter a valid 10-digit number";
  }
  if (!form.city.trim()) errors.city = "City is required";
  return errors;
}

// ─── Shared field styles ──────────────────────────────────────────────────────

const INPUT =
  "w-full rounded-xl border px-4 py-3 pl-10 text-sm text-gray-800 " +
  "bg-white placeholder:text-gray-400 " +
  "focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-transparent " +
  "transition-all duration-150";

const INPUT_ERROR = "border-red-300 bg-red-50 focus:ring-red-400";
const INPUT_NORMAL = "border-gray-200 hover:border-gray-300";

// ─── Field label component ────────────────────────────────────────────────────

function Label({
  children,
  required,
  optional,
}: {
  children: string;
  required?: boolean;
  optional?: boolean;
}) {
  return (
    <p className="mb-1.5 text-[11px] font-bold uppercase tracking-wider text-gray-500">
      {children}
      {required && <span className="ml-0.5 text-red-500">*</span>}
      {optional && (
        <span className="ml-1 font-normal normal-case tracking-normal text-gray-400">
          (optional)
        </span>
      )}
    </p>
  );
}

// ─── Main component ───────────────────────────────────────────────────────────

export default function OnRoadPriceModal({
  car,
  isOpen,
  onClose,
  selectedVariant = "",
}: OnRoadPriceModalProps) {
  const formId = useId();

  const [form, setForm] = useState<FormState>({
    name: "",
    mobile: "",
    email: "",
    pinCode: "",
    city: "",
    state: "",
    variant: selectedVariant,
    message: "",
  });
  const [errors, setErrors] = useState<FormErrors>({});
  const [loading, setLoading] = useState(false);
  const [success, setSuccess] = useState(false);
  const [apiError, setApiError] = useState<string | null>(null);
  const [pinLoading, setPinLoading] = useState(false);
  const [pinSuccess, setPinSuccess] = useState(false);

  const clickTracked = useRef(false);

  // ── Body scroll lock ────────────────────────────────────────────────────────
  useEffect(() => {
    if (isOpen) {
      const prev = document.body.style.overflow;
      document.body.style.overflow = "hidden";
      return () => {
        document.body.style.overflow = prev;
      };
    }
  }, [isOpen]);

  // ── Track click once per open ────────────────────────────────────────────────
  useEffect(() => {
    if (isOpen && !clickTracked.current) {
      clickTracked.current = true;
      trackLeadClick({
        carId: car.id,
        carName: car.name,
        source: "on_road_price",
      }).catch(() => {});
    }
    if (!isOpen) clickTracked.current = false;
  }, [isOpen, car.id, car.name]);

  // ── Reset on open ────────────────────────────────────────────────────────────
  useEffect(() => {
    if (isOpen) {
      setForm({
        name: "",
        mobile: "",
        email: "",
        pinCode: "",
        city: "",
        state: "",
        variant: selectedVariant,
        message: "",
      });
      setErrors({});
      setSuccess(false);
      setApiError(null);
      setPinLoading(false);
      setPinSuccess(false);
    }
  }, [isOpen, selectedVariant]);

  // ── PIN lookup ────────────────────────────────────────────────────────────────

  async function lookupPin(pin: string) {
    setPinLoading(true);
    setPinSuccess(false);
    setErrors((prev) => ({ ...prev, pinCode: undefined }));
    try {
      const res = await fetch(`https://api.postalpincode.in/pincode/${pin}`);
      if (!res.ok) throw new Error("Network error");
      const json = await res.json();
      if (
        json?.[0]?.Status === "Success" &&
        (json[0]?.PostOffice?.length ?? 0) > 0
      ) {
        const po = json[0].PostOffice[0];
        setForm((prev) => ({
          ...prev,
          city: po.District || po.Name || prev.city,
          state: po.State || prev.state,
        }));
        // Clear city validation error now that it's auto-filled
        setErrors((prev) => ({ ...prev, city: undefined, pinCode: undefined }));
        setPinSuccess(true);
      } else {
        setErrors((prev) => ({
          ...prev,
          pinCode: "Invalid PIN code — no records found",
        }));
        setForm((prev) => ({ ...prev, city: "", state: "" }));
      }
    } catch {
      setErrors((prev) => ({
        ...prev,
        pinCode: "Could not verify PIN. Check your connection or enter city manually.",
      }));
    } finally {
      setPinLoading(false);
    }
  }

  // ── Handlers ─────────────────────────────────────────────────────────────────

  function handleChange(field: keyof FormState, value: string) {
    setForm((prev) => ({ ...prev, [field]: value }));
    if (errors[field as keyof FormErrors]) {
      setErrors((prev) => ({ ...prev, [field]: undefined }));
    }
    // Auto-trigger PIN lookup when 6 digits are typed
    if (field === "pinCode") {
      if (value.length === 6) {
        lookupPin(value);
      } else {
        setPinSuccess(false);
      }
    }
  }

  async function handleSubmit(e: React.FormEvent) {
    e.preventDefault();
    const errs = validate(form);
    if (Object.keys(errs).length > 0) {
      setErrors(errs);
      return;
    }
    setLoading(true);
    setApiError(null);
    try {
      await submitLead({
        carId: car.id,
        carName: car.name,
        variant: form.variant || undefined,
        name: form.name.trim(),
        mobile: form.mobile.trim(),
        email: form.email.trim() || undefined,
        pinCode: form.pinCode.trim() || undefined,
        city: form.city.trim(),
        state: form.state.trim() || undefined,
        message: form.message.trim() || undefined,
        source: "on_road_price",
      });
      setSuccess(true);
      setTimeout(() => onClose(), 1500);
    } catch (err: unknown) {
      setApiError(
        err instanceof Error
          ? err.message
          : "Something went wrong. Please try again."
      );
    } finally {
      setLoading(false);
    }
  }

  const hasVariants = (car.variants?.length ?? 0) > 0;

  // ── Render ────────────────────────────────────────────────────────────────────

  return (
    <Dialog.Root
      open={isOpen}
      onOpenChange={(open) => {
        if (!open) onClose();
      }}
    >
      <Dialog.Portal>

        {/* ── Backdrop ────────────────────────────────────────────────────────
            Separate from Dialog.Content so click-outside still works.
            Radix fires onPointerDownOutside relative to the Content element. */}
        <Dialog.Overlay asChild>
          <motion.div
            initial={{ opacity: 0 }}
            animate={{ opacity: 1 }}
            exit={{ opacity: 0 }}
            transition={{ duration: 0.2 }}
            className="fixed inset-0 z-50 bg-black/60 backdrop-blur-sm"
          />
        </Dialog.Overlay>

        {/* ── Dialog content
            Uses a pointer-events-none centering shell so the backdrop's
            click-outside handler can fire.  The card itself gets
            pointer-events-auto.
        ──────────────────────────────────────────────────────────────────── */}
        <Dialog.Content
          className={cn(
            // centering shell
            "fixed inset-0 z-50",
            "flex items-center justify-center",
            "p-4",
            // the shell itself has no pointer events so clicks on the
            // backdrop area reach the Overlay above
            "pointer-events-none",
            // suppress the default focus ring on the shell
            "focus:outline-none"
          )}
          // still allow ESC key and the onPointerDownOutside from Radix
          // onPointerDownOutside is automatically wired to close by Radix
        >
          {/* ── Card — responsive width ────────────────────────────────────
              Mobile  : 95 vw, max 420 px
              Tablet  : 92 vw
              Desktop : max 700 px
          ──────────────────────────────────────────────────────────────── */}
          <motion.div
            initial={{ opacity: 0, scale: 0.96, y: 20 }}
            animate={{ opacity: 1, scale: 1, y: 0 }}
            exit={{ opacity: 0, scale: 0.96, y: 14 }}
            transition={{ type: "spring", damping: 26, stiffness: 340 }}
            className={cn(
              // re-enable pointer events on the actual card
              "pointer-events-auto",
              // responsive width — 95vw mobile, 90vw tablet, 560px desktop cap
              "w-[95vw]",
              "sm:w-[90vw]",
              "max-w-[560px]",
              // card shape
              "rounded-[24px] bg-white shadow-2xl ring-1 ring-black/8",
              // flex column so header/footer can be sticky
              "flex flex-col",
              // generous height — let the scrollable body absorb overflow
              "max-h-[90vh]",
              "overflow-hidden"
            )}
          >
            {/* ════════════════════════════════════════════════════════════
                HEADER — sticky, never scrolls
            ════════════════════════════════════════════════════════════ */}
            <div className="relative shrink-0 bg-gradient-to-r from-blue-600 to-blue-500 px-6 pt-4 pb-5">
              {/* Close — 48 × 48 touch target */}
              <Dialog.Close asChild>
                <button
                  className={cn(
                    "absolute top-[16px] right-[12px]",
                    "w-12 h-12",
                    "flex items-center justify-center",
                    "rounded-full bg-white/15 text-white",
                    "hover:bg-white/25 active:bg-white/35",
                    "transition-colors duration-150",
                    "focus:outline-none focus-visible:ring-2 focus-visible:ring-white/60"
                  )}
                  aria-label="Close"
                >
                  <X className="w-[18px] h-[18px]" strokeWidth={2.5} />
                </button>
              </Dialog.Close>

              <p className="text-[10px] font-black uppercase tracking-[0.2em] text-blue-100 mb-0.5">
                Free Enquiry
              </p>
              <Dialog.Title className="text-[22px] font-black text-white leading-tight pr-14">
                Get On-Road Price
              </Dialog.Title>
              <Dialog.Description className="mt-0.5 text-sm text-blue-100 pr-14 truncate">
                {car.name}
              </Dialog.Description>
            </div>

            {/* ════════════════════════════════════════════════════════════
                BODY — scrolls
            ════════════════════════════════════════════════════════════ */}
            <div className="flex-1 overflow-y-auto overscroll-contain">
              <AnimatePresence mode="wait">

                {/* ── Success state ── */}
                {success && (
                  <motion.div
                    key="success"
                    initial={{ opacity: 0, scale: 0.88 }}
                    animate={{ opacity: 1, scale: 1 }}
                    transition={{ type: "spring", damping: 18, stiffness: 260 }}
                    className="flex flex-col items-center justify-center py-16 px-8 text-center"
                  >
                    <motion.div
                      initial={{ scale: 0 }}
                      animate={{ scale: 1 }}
                      transition={{
                        type: "spring",
                        damping: 12,
                        stiffness: 260,
                        delay: 0.06,
                      }}
                      className="mb-5 flex h-20 w-20 items-center justify-center rounded-full bg-green-100"
                    >
                      <CheckCircle2 className="h-10 w-10 text-green-500" strokeWidth={2} />
                    </motion.div>
                    <h3 className="mb-2 text-[22px] font-black text-gray-900">
                      Thank You!
                    </h3>
                    <p className="max-w-[280px] text-sm leading-relaxed text-gray-500">
                      We will contact you shortly with the on-road price for{" "}
                      <span className="font-semibold text-gray-700">{car.name}</span>.
                    </p>
                  </motion.div>
                )}

                {/* ── Form ── */}
                {!success && (
                  <motion.div
                    key="form"
                    initial={{ opacity: 1 }}
                    exit={{ opacity: 0 }}
                    className="px-6 pt-5 pb-3"
                  >
                    <form id={formId} onSubmit={handleSubmit} noValidate>

                      {/* API-level error */}
                      {apiError && (
                        <div className="mb-4 rounded-xl border border-red-200 bg-red-50 px-4 py-3 text-sm text-red-700">
                          {apiError}
                        </div>
                      )}

                      {/* ── Row 1: Car (read-only) — full width ── */}
                      <div className="mb-4">
                        <Label>Car</Label>
                        <div className="flex items-center gap-3 rounded-xl border border-gray-200 bg-gray-50 px-4 py-3">
                          <Car className="h-4 w-4 shrink-0 text-gray-400" />
                          <span className="truncate text-sm font-semibold text-gray-700">
                            {car.name}
                          </span>
                        </div>
                      </div>

                      {/* ── Row 2: Variant — full width, hidden when no variants ── */}
                      {hasVariants && (
                        <div className="mb-4">
                          <Label optional>Variant</Label>
                          <select
                            value={form.variant}
                            onChange={(e) => handleChange("variant", e.target.value)}
                            className={cn(
                              "w-full rounded-xl border px-4 py-3 text-sm text-gray-800",
                              "bg-white appearance-none",
                              "border-gray-200 hover:border-gray-300",
                              "focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-transparent",
                              "transition-all duration-150"
                            )}
                          >
                            <option value="">Select variant (optional)</option>
                            {car.variants!.map((v) => (
                              <option key={v.name} value={v.name}>
                                {v.name}
                              </option>
                            ))}
                          </select>
                        </div>
                      )}

                      {/* ── Rows 3-4: Name + Mobile — single column ── */}
                      <div className="mb-4 grid grid-cols-1 gap-4">

                        {/* Full Name */}
                        <div>
                          <Label required>Full Name</Label>
                          <div className="relative">
                            <User className="pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-gray-400" />
                            <input
                              type="text"
                              placeholder="Your full name"
                              value={form.name}
                              onChange={(e) => handleChange("name", e.target.value)}
                              autoComplete="name"
                              className={cn(
                                INPUT,
                                errors.name ? INPUT_ERROR : INPUT_NORMAL
                              )}
                            />
                          </div>
                          {errors.name && (
                            <p className="mt-1 text-[11px] font-medium text-red-500">
                              {errors.name}
                            </p>
                          )}
                        </div>

                        {/* Mobile */}
                        <div>
                          <Label required>Mobile Number</Label>
                          <div className="relative">
                            <Phone className="pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-gray-400" />
                            <input
                              type="tel"
                              placeholder="10-digit number"
                              value={form.mobile}
                              inputMode="numeric"
                              onChange={(e) =>
                                handleChange(
                                  "mobile",
                                  e.target.value.replace(/\D/g, "").slice(0, 10)
                                )
                              }
                              maxLength={10}
                              autoComplete="tel"
                              className={cn(
                                INPUT,
                                errors.mobile ? INPUT_ERROR : INPUT_NORMAL
                              )}
                            />
                          </div>
                          {errors.mobile && (
                            <p className="mt-1 text-[11px] font-medium text-red-500">
                              {errors.mobile}
                            </p>
                          )}
                        </div>
                      </div>

                      {/* ── Row 5: Email ── */}
                      <div className="mb-4">
                        <Label optional>Email</Label>
                        <div className="relative">
                          <Mail className="pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-gray-400" />
                          <input
                            type="email"
                            placeholder="your@email.com"
                            value={form.email}
                            onChange={(e) => handleChange("email", e.target.value)}
                            autoComplete="email"
                            className={cn(INPUT, INPUT_NORMAL)}
                          />
                        </div>
                      </div>

                      {/* ── Row 6: PIN Code (auto-fills city + state) ── */}
                      <div className="mb-4">
                        <Label optional>PIN Code</Label>
                        <div className="relative">
                          <MapPin className="pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-gray-400" />
                          <input
                            type="text"
                            inputMode="numeric"
                            placeholder="6-digit PIN (auto-fills city &amp; state)"
                            value={form.pinCode}
                            onChange={(e) =>
                              handleChange(
                                "pinCode",
                                e.target.value.replace(/\D/g, "").slice(0, 6)
                              )
                            }
                            maxLength={6}
                            className={cn(
                              INPUT,
                              "pr-10",
                              errors.pinCode ? INPUT_ERROR : INPUT_NORMAL
                            )}
                          />
                          {/* Lookup status indicator */}
                          <div className="pointer-events-none absolute right-3 top-1/2 -translate-y-1/2">
                            {pinLoading && (
                              <Loader2 className="h-4 w-4 animate-spin text-blue-400" />
                            )}
                            {pinSuccess && !pinLoading && (
                              <CheckCircle2 className="h-4 w-4 text-green-500" />
                            )}
                          </div>
                        </div>
                        {errors.pinCode && (
                          <p className="mt-1 text-[11px] font-medium text-red-500">
                            {errors.pinCode}
                          </p>
                        )}
                        {pinSuccess && !errors.pinCode && (
                          <p className="mt-1 text-[11px] font-medium text-green-600">
                            ✓ Location detected automatically
                          </p>
                        )}
                      </div>

                      {/* ── Row 7: City + State (auto-filled or manually entered) ── */}
                      <div className="mb-4 grid grid-cols-2 gap-3">
                        {/* City */}
                        <div>
                          <Label required>City</Label>
                          <div className="relative">
                            <MapPin className="pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-gray-400" />
                            <input
                              type="text"
                              placeholder="Your city"
                              value={form.city}
                              onChange={(e) => handleChange("city", e.target.value)}
                              autoComplete="address-level2"
                              className={cn(
                                INPUT,
                                errors.city ? INPUT_ERROR : INPUT_NORMAL
                              )}
                            />
                          </div>
                          {errors.city && (
                            <p className="mt-1 text-[11px] font-medium text-red-500">
                              {errors.city}
                            </p>
                          )}
                        </div>
                        {/* State */}
                        <div>
                          <Label optional>State</Label>
                          <div className="relative">
                            <MapPin className="pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-gray-400" />
                            <input
                              type="text"
                              placeholder="State"
                              value={form.state}
                              onChange={(e) => handleChange("state", e.target.value)}
                              className={cn(INPUT, INPUT_NORMAL)}
                            />
                          </div>
                        </div>
                      </div>

                      {/* ── Row 7: Message — full width ── */}
                      <div>
                        <Label optional>Message</Label>
                        <div className="relative">
                          <MessageSquare className="pointer-events-none absolute left-3 top-3.5 h-4 w-4 text-gray-400" />
                          <textarea
                            placeholder="Any specific requirements or questions?"
                            value={form.message}
                            onChange={(e) => handleChange("message", e.target.value)}
                            rows={2}
                            className={cn(
                              INPUT,
                              INPUT_NORMAL,
                              "resize-none leading-relaxed"
                            )}
                          />
                        </div>
                      </div>

                    </form>
                  </motion.div>
                )}
              </AnimatePresence>
            </div>

            {/* ════════════════════════════════════════════════════════════
                FOOTER — sticky, never scrolls, hidden on success
            ════════════════════════════════════════════════════════════ */}
            <AnimatePresence>
              {!success && (
                <motion.div
                  initial={{ opacity: 1 }}
                  exit={{ opacity: 0, y: 8 }}
                  transition={{ duration: 0.15 }}
                  className="shrink-0 border-t border-gray-100 bg-white px-6 py-4"
                >
                  {/* Disclaimer */}
                  <p className="mb-3 text-center text-[10px] leading-snug text-gray-400">
                    By submitting you agree to be contacted regarding this enquiry.
                  </p>

                  {/* Buttons
                      Mobile  : stacked  (flex-col)  Cancel on top, Submit on bottom
                      Desktop : side-by-side (flex-row at sm+)
                  */}
                  <div className="flex flex-col gap-3 sm:flex-row">
                    {/* Cancel */}
                    <Dialog.Close asChild>
                      <button
                        type="button"
                        className={cn(
                          "flex-1 min-h-[48px] rounded-xl",
                          "border border-gray-200 bg-white",
                          "text-sm font-bold text-gray-700",
                          "hover:bg-gray-50 hover:border-gray-300",
                          "active:bg-gray-100",
                          "transition-all duration-150",
                          "focus:outline-none focus-visible:ring-2 focus-visible:ring-gray-400"
                        )}
                      >
                        Cancel
                      </button>
                    </Dialog.Close>

                    {/* Submit — connected via `form` attribute */}
                    <motion.button
                      type="submit"
                      form={formId}
                      disabled={loading}
                      whileHover={{ scale: loading ? 1 : 1.02 }}
                      whileTap={{ scale: loading ? 1 : 0.97 }}
                      className={cn(
                        "flex-[2] min-h-[48px] rounded-xl",
                        "bg-gradient-to-r from-blue-600 to-blue-500",
                        "text-sm font-bold text-white",
                        "shadow-lg shadow-blue-200",
                        "flex items-center justify-center gap-2",
                        "disabled:cursor-not-allowed disabled:opacity-70",
                        "transition-all duration-150",
                        "focus:outline-none focus-visible:ring-2 focus-visible:ring-blue-400"
                      )}
                    >
                      {loading ? (
                        <>
                          <Loader2 className="h-4 w-4 animate-spin" />
                          Submitting…
                        </>
                      ) : (
                        <>
                          <Phone className="h-4 w-4" />
                          Get On-Road Price
                        </>
                      )}
                    </motion.button>
                  </div>
                </motion.div>
              )}
            </AnimatePresence>

          </motion.div>
          {/* end card */}
        </Dialog.Content>

      </Dialog.Portal>
    </Dialog.Root>
  );
}
