/* eslint-disable @typescript-eslint/no-explicit-any */
import React, { useEffect, useState } from "react";
import Select from "react-select";
import CreatableSelect from "react-select/creatable"; // Add CreatableSelect import

// Define the Option type
interface Option {
  id: string;
  name: string;
  code?: string | number;
}
interface SelectFieldProps {
  options: Option[];
  value: Option | null;
  onChange: (option: Option | null) => void;
  errors?: string;
  placeholder?: string;
  isMulti?: boolean;
  isClearable?: boolean;
  isSearchable?: boolean;
  onInputChange?: (inputValue: string) => void;
  className?: string;
  width?: string;
  icon?: React.ReactNode;
  isCreatable?: boolean;
  stringAdd?: boolean;
  name?: string;
  title?: string;
  /**
   * Determines how the select field is used in different contexts.
   *
   * - `0`: Default usage (general dropdown)
   * - `1`: Used for adding address section
   */
  usageType?: number;
  page?: string;
  label?: string;
}

const SelectField: React.FC<SelectFieldProps> = ({
  options,
  value,
  onChange,
  errors,
  placeholder = "Select...",
  isMulti = false,
  isClearable = true,
  isSearchable = true,
  onInputChange,
  className,
  width = "",
  icon,
  isCreatable = false,
  stringAdd = false,
  usageType = 0,
  title = "",
  page = "",
  label = "",
  // name = ""
}) => {
  const [inputValue, setInputValue] = useState("");
  const [localOptions, setLocalOptions] = useState<Option[]>(options);
  const [selectedValues, setSelectedValues] = useState<Option | Option[] | null>(value || (isMulti ? [] : null));
  useEffect(() => {
    setLocalOptions(options)
  },[options])
  useEffect(() => {
    setSelectedValues(value);
  }, [value]);

  const formatLabel = (option: Option): string => {
    if (!option.code) return option.name || "";
    return option.name && option.code !== option.name ? `${option.code} - ${option.name}` : String(option.code);
  };

  const handleSelectChange = (selected: any) => {
    if (isMulti) {
      const mapped = selected?.map((item: any) => ({
        id: item.value,
        name: item.label,
        code: item.label
      })) || [];
      setSelectedValues(mapped);
      onChange(mapped);
    } else {
      const mapped = selected ? { id: selected.value, name: selected.label, code: selected.label } : null;
      setSelectedValues(mapped);
      onChange(mapped);
    }
  };

  const handleCreateOptionString = (inputVal: string) => {
    if (!inputVal) return;
    const newOption: Option = {
      id: inputVal,
      name: inputVal,
      code: inputVal
    };

    const updatedOptions = [...localOptions, newOption];
    setLocalOptions(updatedOptions);

    if (isMulti) {
      const updatedSelected: any = Array.isArray(selectedValues)
        ? [...selectedValues, newOption]
        : [newOption];
      setSelectedValues(updatedSelected);
      onChange(updatedSelected);
    } else {
      setSelectedValues(newOption);
      onChange(newOption);
    }
    setInputValue("");
  };

  const commonProps = {
    options: localOptions.map((opt) => ({
      label: formatLabel(opt),
      value: opt.id
    })),
    value: (() => {
      if (!selectedValues) return null;
      if (isMulti && Array.isArray(selectedValues)) {
        return selectedValues.map((val) => ({
          label: formatLabel(val),
          value: val.id
        }));
      }
      if (!Array.isArray(selectedValues)) {
        return { label: formatLabel(selectedValues), value: selectedValues.id };
      }
      return null;
    })(),
    noOptionsMessage: () => (stringAdd ? null : 'No options'),
    onChange: handleSelectChange,
    onInputChange: (val: string) => {
      setInputValue(val);
      onInputChange?.(val);
      return val;
    },
    onKeyDown: (e: React.KeyboardEvent) => {
      if (stringAdd && (e.key === 'Enter' || e.key === 'Tab')) {
        e.preventDefault();
        if (inputValue.trim()) {
          handleCreateOptionString(inputValue.trim());
        }
      }
    },
    onBlur: () => {
      if (stringAdd && inputValue.trim()) {
        handleCreateOptionString(inputValue.trim());
      }
    },
    onMenuClose: () => {
      if (stringAdd && inputValue.trim()) {
        handleCreateOptionString(inputValue.trim());
      }
    },
    classNamePrefix: "react-select",
    placeholder,
    isMulti,
    isClearable,
    isSearchable,
    getOptionLabel: (option: any) => option.label,
    getOptionValue: (option: any) => option.value,
    filterOption: (option: any, input: string) => {
      const label = option.label?.toLowerCase() || "";
      return label.includes(input.toLowerCase());
    },
    formatCreateLabel: isCreatable
      ? (inputValue: string) => `Add "${inputValue}" as a new ${label}`
      : undefined,
    styles: {
      control: (base: any) => ({
        ...base,
        minHeight: "28px",
        fontSize: "12px",
        padding: "0px 5px 0px 30px",
        borderColor: errors ? "red" : base.borderColor,
        "&:hover": {
          borderColor: errors ? "red" : base.borderColor,
        },
      }),
      valueContainer: (base: any) => ({
        ...base,
        padding: "2px 4px",
      }),
      input: (base: any) => ({
        ...base,
        fontSize: "12px",
      }),
      dropdownIndicator: (base: any) => ({
        ...base,
        padding: "2px",
      }),
      clearIndicator: (base: any) => ({
        ...base,
        padding: "2px",
      }),
    },
    className,
  };

  return (
    <>
      {usageType === 1 ? (
        <>
          <style>
            {`
              .input-style em.select-box-leftIcon {
                right: auto;
                left: 15px;
                margin-top: 3px;            
              }
            `}
          </style>
          <div className="col-lg-4">
            {page === "my-profile" ? (
              <div className="input-outer-box mb-3">
                <div
                  className={`input-style input-style-always-active no-borders has-icon validate-field input-style-select mb-0 ${
                    className || ""
                  } ${errors ? "has-error" : ""}`}
                  style={{ width }}
                >
                  <label className="color-theme opacity-50 text-uppercase font-700 font-10">
                    {title}
                  </label>
                  <em className="select-box-leftIcon opacity-100 font-12 color-blue-dark">
                    <i className={`${icon} || "fa fa-user"`}></i>
                  </em>
                  {isCreatable ? (
                    <CreatableSelect {...commonProps} />
                  ) : (
                    <Select {...commonProps} />
                  )}
                  {/* Error message */}
                </div>
                {errors && <div className="text-danger px-2">{errors}</div>}
              </div>
            ) : (
              <div
                className={`input-style input-style-always-active no-borders has-icon validate-field input-style-select ${
                  className || ""
                } ${errors ? "has-error" : ""}`}
                style={{ width }}
              >
                <label className="color-theme opacity-50 text-uppercase font-700 font-10">
                  {title}
                </label>
                <em className="select-box-leftIcon opacity-100 font-12 color-blue-dark">
                  <i className={`${icon} || "fa fa-user"`}></i>
                </em>
                {isCreatable ? (
                  <CreatableSelect {...commonProps} />
                ) : (
                  <Select {...commonProps} />
                )}
                {/* Error message */}
                {errors && <div className="text-danger px-2">{errors}</div>}
              </div>
            )}
          </div>
        </>
      ) : (
        <>
          <div
            className={`input-style01 input-style-select ${className || ""} ${
              errors ? "has-error" : ""
            }`}
            style={{ width }}
          >
            {/* Icon */}
            {icon && (
              <div
                className="input-icon"
                style={{ position: "absolute", left: "10px" }}
              >
                {icon}
              </div>
            )}

            {/* Choose Select or CreatableSelect */}
            {isCreatable ? (
              <CreatableSelect {...commonProps} />
            ) : (
              <Select {...commonProps} />
            )}

            {/* Error message */}
            {/* {errors && <div className="text-danger px-2">{errors}</div>} */}
          </div>
        </>
      )}
    </>
  );
};

export default SelectField;
