import * as React from "react";

export interface SelectProps {
  value?: string;
  onValueChange?: (value: string) => void;
  defaultValue?: string;
  disabled?: boolean;
  children?: React.ReactNode;
}

export interface SelectTriggerProps {
  id?: string;
  className?: string;
  children?: React.ReactNode;
}

export interface SelectContentProps {
  children?: React.ReactNode;
}

export interface SelectItemProps {
  value: string;
  children?: React.ReactNode;
}

export interface SelectValueProps {
  placeholder?: string;
}

const SelectContext = React.createContext<{
  value?: string;
  onValueChange?: (value: string) => void;
  isOpen: boolean;
  setIsOpen: (open: boolean) => void;
}>({
  isOpen: false,
  setIsOpen: () => {
    // Default no-op
  },
});

export function Select({
  value,
  onValueChange,
  defaultValue,
  children,
}: SelectProps): React.JSX.Element {
  const [isOpen, setIsOpen] = React.useState(false);
  const [internalValue, setInternalValue] = React.useState(defaultValue);

  const currentValue = value ?? internalValue;

  const handleValueChange = (newValue: string): void => {
    if (value === undefined) {
      setInternalValue(newValue);
    }
    onValueChange?.(newValue);
    setIsOpen(false);
  };

  const contextValue: {
    value?: string;
    onValueChange?: (value: string) => void;
    isOpen: boolean;
    setIsOpen: (open: boolean) => void;
  } = { isOpen, setIsOpen };

  if (currentValue !== undefined) {
    contextValue.value = currentValue;
  }
  contextValue.onValueChange = handleValueChange;

  return (
    <SelectContext.Provider value={contextValue}>
      <div className="relative">{children}</div>
    </SelectContext.Provider>
  );
}

export function SelectTrigger({
  id,
  className = "",
  children,
}: SelectTriggerProps): React.JSX.Element {
  const { isOpen, setIsOpen } = React.useContext(SelectContext);

  return (
    <button
      id={id}
      type="button"
      onClick={() => {
        setIsOpen(!isOpen);
      }}
      className={`flex h-10 w-full items-center justify-between rounded-md border border-gray-300 bg-white px-3 py-2 text-sm ${className}`}
    >
      {children}
    </button>
  );
}

export function SelectValue({ placeholder }: SelectValueProps): React.JSX.Element {
  const { value } = React.useContext(SelectContext);

  return <span>{value ?? placeholder}</span>;
}

export function SelectContent({ children }: SelectContentProps): React.JSX.Element | null {
  const { isOpen } = React.useContext(SelectContext);

  if (!isOpen) return null;

  return (
    <div className="absolute z-50 mt-1 max-h-60 w-full overflow-auto rounded-md border border-gray-300 bg-white shadow-lg">
      {children}
    </div>
  );
}

export function SelectItem({ value, children }: SelectItemProps): React.JSX.Element {
  const { onValueChange } = React.useContext(SelectContext);

  return (
    <div
      onClick={() => onValueChange?.(value)}
      className="cursor-pointer px-3 py-2 text-sm hover:bg-gray-100"
    >
      {children}
    </div>
  );
}
