import React, { useState, useEffect } from "react";
import {
  View,
  Pressable,
  TextInput,
  StyleSheet,
  ActivityIndicator,
  Platform,
} from "react-native";
import { useColorScheme } from "nativewind";
import { Text } from "@/components/ui/text";
import {
  ArrowLeft,
  Plus,
  Calendar,
  ChevronDown,
  Trash2,
  Upload,
  CalendarSearch,
} from "@/lib/icons";
import { ScreenWrapper } from "@/components/ScreenWrapper";
import { FormFlow } from "@/components/FormFlow";
import { useSirouRouter } from "@sirou/react-native";
import { AppRoutes } from "@/lib/routes";
import { api, BASE_URL } from "@/lib/api";
import { toast } from "@/lib/toast-store";
import { useAuthStore } from "@/lib/auth-store";
import * as ImagePicker from "expo-image-picker";
import { PickerModal, SelectOption } from "@/components/PickerModal";
import { CalendarGrid } from "@/components/CalendarGrid";
import { CustomerPicker } from "@/components/CustomerPicker";
import { getPlaceholderColor } from "@/lib/colors";
import { getScanData } from "@/lib/scan-cache";

type Item = { id: number; description: string; qty: string; price: string };

const S = StyleSheet.create({
  input: {
    paddingHorizontal: 12,
    paddingVertical: 12,
    fontSize: 12,
    fontWeight: "500",
    borderRadius: 6,
    borderWidth: 1,
    textAlignVertical: "center",
  },
  inputCenter: {
    paddingHorizontal: 12,
    paddingVertical: 10,
    fontSize: 14,
    fontWeight: "500",
    borderRadius: 6,
    borderWidth: 1,
    textAlign: "center",
    textAlignVertical: "center",
  },
});

function useInputColors() {
  const { colorScheme } = useColorScheme();
  const dark = colorScheme === "dark";
  return {
    bg: dark ? "rgba(30,30,30,0.8)" : "rgba(241,245,249,0.2)",
    border: dark ? "rgba(255,255,255,0.08)" : "rgba(203,213,225,0.6)",
    text: dark ? "#f1f5f9" : "#0f172a",
    placeholder: "rgba(100,116,139,0.45)",
  };
}

function Field({
  label,
  value,
  onChangeText,
  placeholder,
  numeric = false,
  center = false,
  flex,
  multiline = false,
}: {
  label: string;
  value: string;
  onChangeText: (v: string) => void;
  placeholder: string;
  numeric?: boolean;
  center?: boolean;
  flex?: number;
  multiline?: boolean;
}) {
  const c = useInputColors();
  return (
    <View style={flex != null ? { flex } : undefined}>
      <Text className="text-[14px] font-sans-bold mb-1.5 ml-1 text-foreground">
        {label}
      </Text>
      <TextInput
        style={[
          center ? S.inputCenter : S.input,
          { backgroundColor: c.bg, borderColor: c.border, color: c.text },
          multiline
            ? { height: 80, paddingTop: 10, textAlignVertical: "top" }
            : {},
        ]}
        placeholder={placeholder}
        placeholderTextColor={c.placeholder}
        value={value}
        onChangeText={onChangeText}
        keyboardType={numeric ? "numeric" : "default"}
        multiline={multiline}
        autoCorrect={false}
        autoCapitalize="none"
      />
    </View>
  );
}

function PickerField({
  label,
  value,
  onPress,
}: {
  label: string;
  value: string;
  onPress: () => void;
}) {
  const c = useInputColors();
  return (
    <View className="flex-1 mb-4">
      <Text className="text-[14px] font-sans-bold mb-1.5 ml-1 text-foreground">
        {label}
      </Text>
      <Pressable
        onPress={onPress}
        className="h-11 px-3 border border-border rounded-[6px] flex-row items-center justify-between"
        style={{ backgroundColor: c.bg, borderColor: c.border }}
      >
        <Text className="text-xs font-sans-bold" style={{ color: c.text }}>
          {value}
        </Text>
        <ChevronDown size={14} color={c.text} strokeWidth={3} />
      </Pressable>
    </View>
  );
}

const STEPS = [
  { key: "customer", label: "Customer" },
  { key: "details", label: "Details" },
  { key: "items", label: "Items" },
  { key: "taxes", label: "Taxes & Notes" },
  { key: "review", label: "Review" },
];

export default function CreateInvoiceScreen() {
  const nav = useSirouRouter<AppRoutes>();
  const [step, setStep] = useState(0);
  const [submitting, setSubmitting] = useState(false);
  const [scanFailures, setScanFailures] = useState(0);

  const [invoiceNumber, setInvoiceNumber] = useState("");
  const [customerName, setCustomerName] = useState("");
  const [customerEmail, setCustomerEmail] = useState("");
  const [customerPhone, setCustomerPhone] = useState("");
  const [description, setDescription] = useState("");
  const [currency, setCurrency] = useState("ETB ");
  const [type, setType] = useState("SALES");
  const [status, setStatus] = useState("DRAFT");
  const [taxAmount, setTaxAmount] = useState("0");
  const [discountAmount, setDiscountAmount] = useState("0");
  const [notes, setNotes] = useState("");

  const [issueDate, setIssueDate] = useState(
    new Date().toISOString().split("T")[0],
  );
  const [dueDate, setDueDate] = useState("");

  const [items, setItems] = useState<Item[]>([
    { id: 1, description: "", qty: "1", price: "" },
  ]);

  const [showCurrency, setShowCurrency] = useState(false);
  const [showType, setShowType] = useState(false);
  const [showStatus, setShowStatus] = useState(false);
  const [showIssueDate, setShowIssueDate] = useState(false);
  const [showDueDate, setShowDueDate] = useState(false);

  const [scanning, setScanning] = useState(false);
  const token = useAuthStore((s) => s.token);

  const { colorScheme } = useColorScheme();
  const isDark = colorScheme === "dark";
  const c = useInputColors();

  useEffect(() => {
    const year = new Date().getFullYear();
    const random = Math.floor(1000 + Math.random() * 9000);
    setInvoiceNumber(`INV-${year}-${random}`);
    const d = new Date();
    d.setDate(d.getDate() + 30);
    setDueDate(d.toISOString().split("T")[0]);

    const scanData = getScanData();
    if (scanData) {
      if (scanData.invoiceNumber) setInvoiceNumber(scanData.invoiceNumber);
      const name =
        scanData.customerName
          ?.trim()
          ?.replace(/^(Customer Name:|Bill To:)\s*/i, "") || "";
      if (name) setCustomerName(name);
      if (scanData.customerEmail) setCustomerEmail(scanData.customerEmail);
      if (scanData.customerPhone) setCustomerPhone(scanData.customerPhone.replace(/^\+251/, ""));
      if (scanData.description) setDescription(scanData.description);
      if (scanData.currency) setCurrency(scanData.currency);
      if (scanData.taxAmount != null) setTaxAmount(String(scanData.taxAmount));
      if (scanData.issueDate) {
        try {
          setIssueDate(
            new Date(scanData.issueDate).toISOString().split("T")[0],
          );
        } catch (_) {}
      }
      if (scanData.dueDate) {
        try {
          setDueDate(new Date(scanData.dueDate).toISOString().split("T")[0]);
        } catch (_) {}
      }
      if (scanData.items && scanData.items.length > 0) {
        setItems(
          scanData.items.map((item: any, idx: number) => ({
            id: idx + 1,
            description: item.description || "",
            qty: String(item.quantity || "1"),
            price: String(item.unitPrice || item.total || ""),
          })),
        );
      }
    }
  }, []);

  const handlePickImage = async () => {
    try {
      const { status } =
        await ImagePicker.requestMediaLibraryPermissionsAsync();
      if (status !== "granted") {
        toast.error(
          "Permission Denied",
          "Need gallery access to scan invoices.",
        );
        return;
      }
      const result = await ImagePicker.launchImageLibraryAsync({
        mediaTypes: ImagePicker.MediaTypeOptions.Images,
        allowsEditing: true,
        quality: 0.8,
      });
      if (!result.canceled && result.assets?.[0]) {
        await processImage(result.assets[0].uri);
      }
    } catch (e: any) {
      toast.error("Picker Failed", "Could not launch gallery.");
    }
  };

  const processImage = async (uri: string) => {
    setScanning(true);
    toast.info("Processing...", "Uploading for AI extraction.");
    try {
      const formData = new FormData();
      const fileExt = uri.split(".").pop() || "jpg";
      formData.append("file", {
        uri: Platform.OS === "android" ? uri : uri.replace("file://", ""),
        name: `invoice-${Date.now()}.${fileExt}`,
        type: `image/${fileExt === "jpg" ? "jpeg" : fileExt}`,
      } as any);

      const response = await fetch(`${BASE_URL}scan/invoice`, {
        method: "POST",
        headers: {
          Authorization: `Bearer ${token}`,
          Accept: "application/json",
        },
        body: formData,
      });
      if (!response.ok)
        throw new Error(
          (await response.json().catch(() => ({}))).message ||
            "Extraction failed",
        );
      const scanResult = await response.json();
      if (!scanResult.success)
        throw new Error(scanResult.message || "Extraction failed");
      toast.success("Success!", "Data extracted.");
      const ocr = scanResult.data || {};
      if (ocr.invoiceNumber) setInvoiceNumber(ocr.invoiceNumber);
      const name = (ocr.customerName?.trim() || "").replace(
        /^(Customer Name:|Bill To:)\s*/i,
        "",
      );
      if (name) setCustomerName(name);
      if (ocr.customerEmail) setCustomerEmail(ocr.customerEmail);
      if (ocr.customerPhone) setCustomerPhone(ocr.customerPhone.replace(/^\+251/, ""));
      if (ocr.description) setDescription(ocr.description);
      if (ocr.currency) setCurrency(ocr.currency);
      if (ocr.taxAmount != null) setTaxAmount(String(ocr.taxAmount));
      if (ocr.issueDate) {
        try {
          setIssueDate(new Date(ocr.issueDate).toISOString().split("T")[0]);
        } catch (_) {}
      }
      if (ocr.dueDate) {
        try {
          setDueDate(new Date(ocr.dueDate).toISOString().split("T")[0]);
        } catch (_) {}
      }
      if (ocr.items?.length) {
        setItems(
          ocr.items.map((item: any, idx: number) => ({
            id: idx + 1,
            description: item.description || "",
            qty: String(item.quantity || "1"),
            price: String(item.unitPrice || item.total || ""),
          })),
        );
      }

      await handleSubmit();
    } catch (err: any) {
      const failures = scanFailures + 1;
      setScanFailures(failures);
      if (failures >= 2) {
        toast.warning("Scan failed", "Scan failed, fill details below");
      } else {
        toast.warning("Extraction failed", "Extraction failed, try again");
      }
    } finally {
      setScanning(false);
    }
  };

  const addItem = () => {
    const newId =
      items.length > 0 ? Math.max(...items.map((i) => i.id)) + 1 : 1;
    setItems([...items, { id: newId, description: "", qty: "1", price: "" }]);
  };
  const removeItem = (id: number) => setItems(items.filter((i) => i.id !== id));
  const updateField = (id: number, field: keyof Item, value: string) =>
    setItems(items.map((i) => (i.id === id ? { ...i, [field]: value } : i)));

  const subtotal = items.reduce(
    (s, i) => s + (parseFloat(i.qty) || 0) * (parseFloat(i.price) || 0),
    0,
  );
  const total =
    subtotal + (parseFloat(taxAmount) || 0) - (parseFloat(discountAmount) || 0);

  const handleNext = () => {
    if (step === 0) {
      if (!customerName.trim()) {
        toast.error("Validation", "Customer name is required");
        return;
      }
    }
    if (step === 1) {
      if (!invoiceNumber) {
        toast.error("Validation", "Invoice number is required");
        return;
      }
    }
    setStep(step + 1);
  };

  const handleSubmit = async () => {
    const validItems = items.filter((i) => i.description.trim());
    if (validItems.length === 0) {
      toast.error(
        "Validation",
        "At least one item with description is required",
      );
      return;
    }
    setSubmitting(true);
    try {
      await api.invoices.create({
        body: {
          invoiceNumber,
          customerName,
          customerEmail,
          customerPhone: customerPhone ? `+251${customerPhone}` : "",
          amount: Number(total.toFixed(2)),
          currency,
          type,
          status,
          issueDate: new Date(issueDate).toISOString(),
          dueDate: new Date(dueDate).toISOString(),
          description,
          notes,
          taxAmount: parseFloat(taxAmount) || 0,
          discountAmount: parseFloat(discountAmount) || 0,
          isScanned: false,
          scannedData: { sellerTIN: "123456", items: [] },
          items: validItems.map((item) => ({
            description: item.description.trim(),
            quantity: parseFloat(item.qty) || 0,
            unitPrice: parseFloat(item.price) || 0,
            total: Number(
              (
                (parseFloat(item.qty) || 0) * (parseFloat(item.price) || 0)
              ).toFixed(2),
            ),
          })),
        },
      });
      toast.success("Success", "Invoice created!");
      nav.back();
    } catch (error: any) {
      const msg =
        error?.response?.data?.message ||
        error?.data?.message ||
        error?.message ||
        "Failed to create invoice";
      toast.error("Error", msg);
      throw error;
    } finally {
      setSubmitting(false);
    }
  };

  const currencies = ["USD", "ETB", "EUR", "GBP", "KES", "ZAR"];
  const invoiceTypes = ["SALES", "PURCHASE", "SERVICE"];
  const invoiceStatuses = ["DRAFT", "PENDING", "PAID"];

  return (
    <ScreenWrapper className="bg-background">
      <FormFlow
        steps={STEPS}
        currentStep={step}
        onNext={handleNext}
        onBack={() => setStep(step - 1)}
        onComplete={handleSubmit}
        loading={submitting}
        completeLabel="Create Invoice"
      >
        {step === 0 && (
          <View className="gap-5">
            <Pressable
              onPress={handlePickImage}
              disabled={scanning}
              className="bg-primary/10 border border-primary/20 rounded-[8px] p-4 flex-row items-center gap-3.5 "
            >
              {scanning ? (
                <ActivityIndicator color="#ea580c" size="small" />
              ) : (
                <Upload color="#ea580c" size={20} strokeWidth={2.5} />
              )}
              <View className="flex-1">
                <Text className="text-primary font-sans-black text-xs">
                  Scan from Gallery
                </Text>
                <Text className="text-muted-foreground text-[9px] font-sans-bold mt-0.5">
                  Upload image to auto-fill form
                </Text>
              </View>
            </Pressable>

            <Text className="text-[18px] font-sans-bold text-foreground tracking-tight">
              Customer Information
            </Text>
            <View className="gap-4">
              <View>
                <Text className="text-[14px] font-sans-bold mb-1.5 ml-1 text-foreground">
                  Customer Name
                </Text>
                <CustomerPicker
                  value={customerName}
                  onSelect={(c) => {
                    setCustomerName(c.name);
                    setCustomerEmail(c.email);
                    setCustomerPhone(c.phone.replace("+251", ""));
                  }}
                  placeholder="Select or search for a customer"
                />
              </View>
              <View className="flex-row gap-4 my-4">
                <Field
                  label="Email"
                  value={customerEmail}
                  onChangeText={setCustomerEmail}
                  placeholder="billing@acme.com"
                  flex={1}
                />
              </View>
              <View>
                <Text className="text-[14px] font-sans-bold mb-1.5 ml-1 text-foreground">
                  Phone
                </Text>
                <View className="flex-row items-center h-11 px-3 border border-border rounded-[6px]" style={{ backgroundColor: c.bg, borderColor: c.border }}>
                  <Text className="text-foreground font-sans-bold text-xs">+251</Text>
                  <TextInput
                    className="flex-1 ml-2 text-foreground text-xs font-sans-medium"
                    placeholder="912345678"
                    placeholderTextColor={c.placeholder}
                    value={customerPhone}
                    onChangeText={setCustomerPhone}
                    keyboardType="phone-pad"
                    maxLength={9}
                    style={{ textAlignVertical: "center" }}
                  />
                </View>
              </View>
            </View>
          </View>
        )}

        {step === 1 && (
          <View className="gap-5">
            <Text className="text-[18px] font-sans-bold text-foreground tracking-tight">
              Invoice Details
            </Text>
            <View className="bg-card rounded-[6px] gap-4">
              <Field
                label="Invoice Number"
                value={invoiceNumber}
                onChangeText={setInvoiceNumber}
                placeholder="e.g. INV-2024-001"
              />
              <Field
                label="Description"
                value={description}
                onChangeText={setDescription}
                placeholder="e.g. Web Development Services"
              />
              <View className="flex-row gap-4">
                <PickerField
                  label="Issue Date"
                  value={issueDate}
                  onPress={() => setShowIssueDate(true)}
                />
                <PickerField
                  label="Due Date"
                  value={dueDate || "Select"}
                  onPress={() => setShowDueDate(true)}
                />
              </View>
              <View className="flex-row gap-4">
                <PickerField
                  label="Currency"
                  value={currency}
                  onPress={() => setShowCurrency(true)}
                />
                <PickerField
                  label="Type"
                  value={type}
                  onPress={() => setShowType(true)}
                />
              </View>
              <PickerField
                label="Status"
                value={status}
                onPress={() => setShowStatus(true)}
              />
            </View>
          </View>
        )}

        {step === 2 && (
          <View className="gap-5">
            <View className="flex-row items-center justify-between">
              <Text className="text-[18px] font-sans-bold text-foreground tracking-tight">
                Billable Items
              </Text>
              <Pressable
                onPress={addItem}
                className="flex-row items-center gap-1 px-3 py-1.5 rounded-[6px] bg-primary/10 border border-primary/20"
              >
                <Plus color="#ea580c" size={10} strokeWidth={2.5} />
                <Text className="text-primary text-[8px] font-sans-bold">
                  Add
                </Text>
              </Pressable>
            </View>
            <View className="gap-3">
              {items.map((item, index) => (
                <View
                  key={item.id}
                  className="bg-card rounded-[6px] p-4 border border-border"
                >
                  <View className="flex-row justify-between items-center mb-3">
                    <Text className="text-[16px] font-sans-bold text-foreground">
                      Item {index + 1}
                    </Text>
                    <Pressable onPress={() => removeItem(item.id)} hitSlop={8}>
                      <Trash2 color="#ef4444" size={16} />
                    </Pressable>
                  </View>
                  <Field
                    label="Description"
                    placeholder="e.g. UI Design"
                    value={item.description}
                    onChangeText={(v) => updateField(item.id, "description", v)}
                  />
                  <View className="flex-row gap-3 mt-4">
                    <Field
                      label="Qty"
                      placeholder="1"
                      numeric
                      center
                      value={item.qty}
                      onChangeText={(v) => updateField(item.id, "qty", v)}
                      flex={1}
                    />
                    <Field
                      label="Price"
                      placeholder="0.00"
                      numeric
                      value={item.price}
                      onChangeText={(v) => updateField(item.id, "price", v)}
                      flex={3}
                    />
                  </View>
                </View>
              ))}
            </View>
          </View>
        )}

        {step === 3 && (
          <View className="gap-5">
            <Text className="text-[18px] font-sans-bold text-foreground tracking-tight">
              Taxes & Notes
            </Text>
            <View className="bg-card rounded-[6px] gap-4">
              <View className="flex-row gap-4">
                <Field
                  label="Tax Amount"
                  value={taxAmount}
                  onChangeText={setTaxAmount}
                  placeholder="0.00"
                  numeric
                  flex={1}
                />
                <Field
                  label="Discount"
                  value={discountAmount}
                  onChangeText={setDiscountAmount}
                  placeholder="0.00"
                  numeric
                  flex={1}
                />
              </View>
            </View>
            <View className="bg-card rounded-[6px]">
              <Field
                label="Notes"
                value={notes}
                onChangeText={setNotes}
                placeholder="e.g. Payment due within 30 days"
                multiline
              />
            </View>
          </View>
        )}

        {step === 4 && (
          <View className="gap-5">
            <Text className="text-[18px] font-sans-bold text-foreground tracking-tight">
              Summary
            </Text>

            <View className="bg-card rounded-[6px] p-4 border border-border gap-3">
              <View className="flex-row justify-between">
                <Text className="text-[14px] text-foreground font-sans-bold">
                  Customer
                </Text>
                <Text className="text-[14px] text-foreground font-sans-bold">
                  {customerName}
                </Text>
              </View>
              {(customerEmail || customerPhone) && (
                <View className="flex-row justify-between">
                  <Text className="text-[14px] text-foreground font-sans-bold">
                    Contact
                  </Text>
                  <Text className="text-[14px] text-foreground font-sans-bold">
                    {customerEmail || (customerPhone ? `+251${customerPhone}` : "")}
                  </Text>
                </View>
              )}
              <View className="border-t border-border/40 my-1" />
              <View className="flex-row justify-between">
                <Text className="text-[14px] text-foreground font-sans-bold">
                  Invoice #
                </Text>
                <Text className="text-[14px] text-foreground font-sans-bold">
                  {invoiceNumber}
                </Text>
              </View>
              <View className="flex-row justify-between">
                <Text className="text-[14px] text-foreground font-sans-bold">
                  Items
                </Text>
                <Text className="text-[14px] text-foreground font-sans-bold">
                  {items.filter((i) => i.description.trim()).length} items
                </Text>
              </View>
              <View className="flex-row justify-between">
                <Text className="text-[14px] text-foreground font-sans-bold">
                  Subtotal
                </Text>
                <Text className="text-[14px] text-foreground font-sans-bold">
                  {currency} {subtotal.toLocaleString()}
                </Text>
              </View>
              {parseFloat(taxAmount) > 0 && (
                <View className="flex-row justify-between">
                  <Text className="text-[14px] text-muted-foreground font-sans-bold">
                    Tax
                  </Text>
                  <Text className="text-[14px] text-foreground font-sans-bold">
                    {currency} {parseFloat(taxAmount).toFixed(2)}
                  </Text>
                </View>
              )}
              {parseFloat(discountAmount) > 0 && (
                <View className="flex-row justify-between">
                  <Text className="text-[14px] text-muted-foreground font-sans-bold">
                    Discount
                  </Text>
                  <Text className="text-[14px] text-destructive font-sans-bold">
                    -{currency} {parseFloat(discountAmount).toFixed(2)}
                  </Text>
                </View>
              )}
              <View className="border-t border-border/40 my-1" />
              <View className="flex-row justify-between">
                <Text className="text-[18px] text-foreground font-sans-bold">
                  Total
                </Text>
                <Text className="text-[18px] text-primary font-sans-bold">
                  {currency}{" "}
                  {total.toLocaleString("en-US", { minimumFractionDigits: 2 })}
                </Text>
              </View>
            </View>
          </View>
        )}
      </FormFlow>

      <PickerModal
        visible={showCurrency}
        onClose={() => setShowCurrency(false)}
        title="Currency"
      >
        {currencies.map((c) => (
          <SelectOption
            key={c}
            label={c}
            value={c}
            selected={currency === c}
            onSelect={(v) => {
              setCurrency(v);
              setShowCurrency(false);
            }}
          />
        ))}
      </PickerModal>
      <PickerModal
        visible={showType}
        onClose={() => setShowType(false)}
        title="Invoice Type"
      >
        {invoiceTypes.map((t) => (
          <SelectOption
            key={t}
            label={t}
            value={t}
            selected={type === t}
            onSelect={(v) => {
              setType(v);
              setShowType(false);
            }}
          />
        ))}
      </PickerModal>
      <PickerModal
        visible={showStatus}
        onClose={() => setShowStatus(false)}
        title="Status"
      >
        {invoiceStatuses.map((s) => (
          <SelectOption
            key={s}
            label={s}
            value={s}
            selected={status === s}
            onSelect={(v) => {
              setStatus(v);
              setShowStatus(false);
            }}
          />
        ))}
      </PickerModal>
      <PickerModal
        visible={showIssueDate}
        onClose={() => setShowIssueDate(false)}
        title="Issue Date"
      >
        <CalendarGrid
          selectedDate={issueDate}
          onSelect={(v) => {
            setIssueDate(v);
            setShowIssueDate(false);
          }}
        />
      </PickerModal>
      <PickerModal
        visible={showDueDate}
        onClose={() => setShowDueDate(false)}
        title="Due Date"
      >
        <CalendarGrid
          selectedDate={dueDate}
          onSelect={(v) => {
            setDueDate(v);
            setShowDueDate(false);
          }}
        />
      </PickerModal>
    </ScreenWrapper>
  );
}
