"use client";

import React, { useState } from "react";
import { Input } from "@/components/ui/input";
import { Switch } from "@/components/ui/switch";
import {
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
} from "@/components/ui/select";
import { Textarea } from "@/components/ui/textarea";
import { Label } from "@/components/ui/label";
import { Button } from "@/components/ui/button";
import { Checkbox } from "@/components/ui/checkbox";
import { Popover, PopoverContent, PopoverTrigger } from "@/components/ui/popover";
import {
  Command,
  CommandEmpty,
  CommandGroup,
  CommandInput,
  CommandItem,
  CommandList,
} from "@/components/ui/command";
import { Plus, X, Check, ChevronsUpDown } from "lucide-react";
import { cn } from "@/lib/utils";
import { ConfigFieldDefinition, ConfigOption } from "./ConfigPanelTypes";

interface ConfigFieldProps<T = any> {
  field: ConfigFieldDefinition<T>;
  value: any;
  onChange: (key: string, value: any) => void;
  tableColumns?: ConfigOption[];
}

export function ConfigField<T>({
  field,
  value,
  onChange,
  tableColumns,
}: ConfigFieldProps<T>) {
  const [comboboxOpen, setComboboxOpen] = useState(false);

  const handleChange = (newValue: any) => {
    onChange(field.key, newValue);
  };

  const renderField = () => {
    switch (field.type) {
      case "text":
        return (
          <Input
            value={value ?? ""}
            onChange={(e) => handleChange(e.target.value)}
            placeholder={field.placeholder}
            className="h-7 text-xs"
          />
        );

      case "number":
        return (
          <Input
            type="number"
            value={value ?? ""}
            onChange={(e) =>
              handleChange(
                e.target.value === "" ? undefined : Number(e.target.value),
              )
            }
            placeholder={field.placeholder}
            min={field.min}
            max={field.max}
            step={field.step}
            className="h-7 text-xs"
          />
        );

      case "switch":
        return (
          <Switch
            checked={!!value}
            onCheckedChange={handleChange}
          />
        );

      case "select":
        return (
          <Select
            value={value ?? ""}
            onValueChange={handleChange}
          >
            <SelectTrigger className="h-7 text-xs">
              <SelectValue placeholder={field.placeholder || "선택"} />
            </SelectTrigger>
            <SelectContent>
              {(field.options || []).map((opt) => (
                <SelectItem key={opt.value} value={opt.value} className="text-xs">
                  {opt.label}
                </SelectItem>
              ))}
            </SelectContent>
          </Select>
        );

      case "textarea":
        return (
          <Textarea
            value={value ?? ""}
            onChange={(e) => handleChange(e.target.value)}
            placeholder={field.placeholder}
            className="text-xs"
            rows={3}
          />
        );

      case "color":
        return (
          <div className="flex items-center gap-1.5">
            <input
              type="color"
              value={value ?? "#000000"}
              onChange={(e) => handleChange(e.target.value)}
              className="h-7 w-7 cursor-pointer rounded border"
            />
            <Input
              value={value ?? ""}
              onChange={(e) => handleChange(e.target.value)}
              placeholder="#000000"
              className="h-7 flex-1 text-xs"
            />
          </div>
        );

      case "slider":
        return (
          <div className="flex items-center gap-1.5">
            <Input
              type="number"
              value={value ?? field.min ?? 0}
              onChange={(e) => handleChange(Number(e.target.value))}
              min={field.min}
              max={field.max}
              step={field.step}
              className="h-7 w-16 text-xs"
            />
            <span className="text-muted-foreground text-[9px]">
              {field.min ?? 0}~{field.max ?? 100}
            </span>
          </div>
        );

      case "multi-select":
        return (
          <div className="space-y-0.5">
            {(field.options || []).map((opt) => {
              const selected = Array.isArray(value) && value.includes(opt.value);
              return (
                <label
                  key={opt.value}
                  className="flex cursor-pointer items-center gap-2 rounded px-1 py-0.5 hover:bg-muted"
                >
                  <input
                    type="checkbox"
                    checked={selected}
                    onChange={() => {
                      const current = Array.isArray(value) ? [...value] : [];
                      if (selected) {
                        handleChange(current.filter((v: string) => v !== opt.value));
                      } else {
                        handleChange([...current, opt.value]);
                      }
                    }}
                    className="rounded"
                  />
                  <span className="text-xs">{opt.label}</span>
                </label>
              );
            })}
          </div>
        );

      case "key-value": {
        const entries: Array<[string, string]> = Object.entries(
          (value as Record<string, string>) || {},
        );
        return (
          <div className="space-y-1">
            {entries.map(([k, v], idx) => (
              <div key={idx} className="flex items-center gap-1">
                <Input
                  value={k}
                  onChange={(e) => {
                    const newObj = { ...(value || {}) };
                    delete newObj[k];
                    newObj[e.target.value] = v;
                    handleChange(newObj);
                  }}
                  placeholder="키"
                  className="h-7 flex-1 text-xs"
                />
                <Input
                  value={v}
                  onChange={(e) => {
                    handleChange({ ...(value || {}), [k]: e.target.value });
                  }}
                  placeholder="값"
                  className="h-7 flex-1 text-xs"
                />
                <Button
                  variant="ghost"
                  size="icon"
                  className="h-7 w-7"
                  onClick={() => {
                    const newObj = { ...(value || {}) };
                    delete newObj[k];
                    handleChange(newObj);
                  }}
                >
                  <X className="h-3 w-3" />
                </Button>
              </div>
            ))}
            <Button
              variant="outline"
              size="sm"
              className="h-7 w-full text-xs"
              onClick={() => {
                handleChange({ ...(value || {}), "": "" });
              }}
            >
              <Plus className="mr-1 h-3 w-3" />
              추가
            </Button>
          </div>
        );
      }

      case "column-picker": {
        const options = tableColumns || field.options || [];
        return (
          <Select
            value={value ?? ""}
            onValueChange={handleChange}
          >
            <SelectTrigger className="h-7 text-xs">
              <SelectValue placeholder={field.placeholder || "컬럼 선택"} />
            </SelectTrigger>
            <SelectContent>
              {options.map((opt) => (
                <SelectItem key={opt.value} value={opt.value} className="text-xs">
                  {opt.label}
                </SelectItem>
              ))}
            </SelectContent>
          </Select>
        );
      }

      case "checkbox":
        return (
          <div className="flex items-center gap-2">
            <Checkbox
              id={`field-${field.key}`}
              checked={!!value}
              onCheckedChange={handleChange}
            />
            {field.description && (
              <label
                htmlFor={`field-${field.key}`}
                className="cursor-pointer text-xs text-muted-foreground"
              >
                {field.description}
              </label>
            )}
          </div>
        );

      case "combobox": {
        const options = field.options || [];
        const selectedLabel = options.find((opt) => opt.value === value)?.label;
        return (
          <Popover open={comboboxOpen} onOpenChange={setComboboxOpen}>
            <PopoverTrigger asChild>
              <Button
                variant="outline"
                role="combobox"
                aria-expanded={comboboxOpen}
                className="h-7 w-full justify-between text-xs font-normal"
              >
                <span className="truncate">
                  {selectedLabel || field.placeholder || "선택"}
                </span>
                <ChevronsUpDown className="ml-1 h-3 w-3 shrink-0 opacity-50" />
              </Button>
            </PopoverTrigger>
            <PopoverContent
              className="p-0"
              style={{ width: "var(--radix-popover-trigger-width)" }}
              align="start"
            >
              <Command>
                <CommandInput placeholder="검색..." className="text-xs" />
                <CommandList>
                  <CommandEmpty className="py-2 text-center text-xs">
                    결과 없음
                  </CommandEmpty>
                  <CommandGroup>
                    {options.map((opt) => (
                      <CommandItem
                        key={opt.value}
                        value={opt.value}
                        onSelect={(currentValue) => {
                          handleChange(currentValue === value ? "" : currentValue);
                          setComboboxOpen(false);
                        }}
                        className="text-xs"
                      >
                        <Check
                          className={cn(
                            "mr-1.5 h-3 w-3",
                            value === opt.value ? "opacity-100" : "opacity-0",
                          )}
                        />
                        {opt.label}
                      </CommandItem>
                    ))}
                  </CommandGroup>
                </CommandList>
              </Command>
            </PopoverContent>
          </Popover>
        );
      }

      default:
        return null;
    }
  };

  // textarea, multi-select, key-value는 전체 폭 수직 레이아웃
  const isFullWidth = ["textarea", "multi-select", "key-value"].includes(field.type);
  // checkbox는 description을 인라인으로 표시하므로 별도 처리
  const isCheckbox = field.type === "checkbox";

  if (isFullWidth) {
    return (
      <div className="py-1.5">
        <Label className="mb-1 block text-xs text-muted-foreground">{field.label}</Label>
        {field.description && !isCheckbox && (
          <p className="text-muted-foreground/60 mb-1 text-[9px]">{field.description}</p>
        )}
        {renderField()}
      </div>
    );
  }

  // switch, checkbox: 라벨 왼쪽, 컨트롤 오른쪽 (고정폭 없이)
  if (field.type === "switch" || isCheckbox) {
    return (
      <div className="flex items-center justify-between py-1.5">
        <Label className="mr-3 truncate text-xs text-muted-foreground">{field.label}</Label>
        {renderField()}
      </div>
    );
  }

  // 기본: 수평 property row (라벨 왼쪽, 컨트롤 오른쪽 고정폭)
  return (
    <div className="flex items-center justify-between py-1.5">
      <Label className="mr-3 min-w-0 shrink truncate text-xs text-muted-foreground">
        {field.label}
      </Label>
      <div className="w-[140px] flex-shrink-0">
        {renderField()}
      </div>
    </div>
  );
}
