import { useForm, SubmitHandler } from 'react-hook-form';
import { AxiosResponse } from 'axios';
import { useEffect, useState } from 'react';
import LoadingWheel from '../LoadingWheel.tsx';
import { Search } from 'lucide-react';
import { ContactsProps } from '@/types/types.ts';
import { useChat } from '@/context/chat/useChat.ts';
import { axiosClient } from '@/utils/axiosClient.ts';

type Input = {
  contact: string;
};

function ContactForm() {
  const { setContactsList, initializeContact } = useChat();
  const { register, handleSubmit, reset, watch } = useForm<Input>();
  const contactInput = watch('contact');
  const [suggestions, setSuggestions] = useState<string[]>([]);
  const [isLoading, setIsLoading] = useState<boolean>(false);
  const [notFound, setNotFound] = useState<boolean>(false);
  const [selectedIndex, setSelectedIndex] = useState<number>(0);

  useEffect(() => {
    const fetchSuggestions = async () => {
      if (contactInput?.length >= 3) {
        try {
          setIsLoading(true);
          const response: AxiosResponse<string[]> = await axiosClient.get(
            `/api/chat/contacts/suggestions/${contactInput}`,
          );
          setSuggestions(response.data);
          setSelectedIndex(0); // Reset selection to first item when suggestions update
          if (response.data?.length < 1) {
            setIsLoading(false);
            setNotFound(true);
          } else {
            setIsLoading(false);
            setNotFound(false);
          }
        } catch (error) {
          setIsLoading(false);
          console.error('Error fetching suggestions:', error);
        }
      } else {
        setNotFound(false);
        setIsLoading(false);
        setSuggestions([]);
      }
    };

    const delay = setTimeout(() => {
      fetchSuggestions();
    }, 300);

    return () => clearTimeout(delay);
  }, [contactInput]);

  const submitContact: SubmitHandler<Input> = async (data) => {
    const contactToSubmit =
      suggestions.length > 0 ? suggestions[selectedIndex] : data.contact.trim();

    try {
      setContactsList((prevContacts) => {
        if (prevContacts.some((c) => c.username === contactToSubmit)) {
          return prevContacts;
        }
        return prevContacts;
      });

      console.log('Submit contact: ', contactToSubmit);
      const response: AxiosResponse<ContactsProps> = await axiosClient.post(
        `/api/chat/contact/${contactToSubmit}`,
      );

      console.log('contact post response: ', response.data);
      initializeContact(response.data);

      setContactsList((prevContacts) => {
        if (!prevContacts.some((c) => c.username === contactToSubmit)) {
          return [...prevContacts, response.data];
        }
        return prevContacts;
      });

      reset({ contact: '' });
      setSuggestions([]);
    } catch (error) {
      console.error('Error adding contact:', error);
    }
  };

  const handleKeyDown = (e: React.KeyboardEvent<HTMLInputElement>) => {
    switch (e.key) {
      case 'ArrowDown':
        e.preventDefault();
        setSelectedIndex((prev) => (prev + 1) % suggestions.length);
        break;
      case 'ArrowUp':
        e.preventDefault();
        setSelectedIndex(
          (prev) => (prev - 1 + suggestions.length) % suggestions.length,
        );
        break;
      case 'Enter':
        if (suggestions?.length > 0) {
          e.preventDefault();
          reset({ contact: suggestions[selectedIndex] });
          handleSubmit(submitContact)();
        }
        break;
      case 'Escape':
        e.preventDefault();
        reset({ contact: '' });
        break;
    }
  };

  return (
    <>
      <div>
        <h1 className="text-xl font-semibold text-gray-200 text-left p-4">
          Chats
        </h1>
        <hr className="border-b border-zinc-800" />
        <form onSubmit={handleSubmit(submitContact)}>
          <div className="p-4">
            <div className="relative">
              <input
                type="text"
                placeholder="Search for user"
                className="w-full bg-zinc-900 rounded-lg py-2 pl-10 focus:border-1 focus:ring-0 focus:border-emerald-800"
                onKeyDown={handleKeyDown}
                {...register('contact', {
                  minLength: 4,
                  maxLength: 20,
                })}
              />
              <Search
                className="absolute left-3 top-2.5 text-gray-400"
                size={18}
              />
            </div>
          </div>
        </form>
        <div className="m-1">
          {suggestions?.length > 0 ? (
            <ul className="text-left p-2 bg-gray-900 shadow-md rounded-md w-full border">
              {suggestions.map((suggestion, index) => (
                <li
                  key={suggestion}
                  className={`p-1 cursor-pointer rounded-md mt-1 mb-1 ${
                    index === selectedIndex
                      ? 'bg-gray-500'
                      : 'hover:bg-gray-500'
                  }`}
                  onClick={() => {
                    reset({ contact: suggestion });
                    handleSubmit(() =>
                      submitContact({ contact: suggestion }),
                    )();
                    setSuggestions([]);
                  }}
                >
                  {suggestion}
                </li>
              ))}
            </ul>
          ) : isLoading ? (
            <LoadingWheel />
          ) : null}
          {notFound ? (
            <p className="p-1 bg-gray-800 shadow-md rounded-md w-full border text-gray-400">
              user not found
            </p>
          ) : null}
        </div>
      </div>
    </>
  );
}

export default ContactForm;
