"use client"

import {
  useCallback,
  useEffect,
  useMemo,
  useRef,
  useState,
  type KeyboardEvent,
} from "react"
import { useRouter } from "next/navigation"
import { Search, X } from "lucide-react"
import { Button } from "@/components/ui/button"
import { MAIL_SEARCH_SUGGESTIONS_DROPDOWN_CLASS } from "@/lib/mail-chrome-classes"
import { DRIVE_SEARCH_INPUT_WRAP_CLASS } from "@/lib/drive/drive-chrome-classes"
import { searchMailSettings } from "@/lib/mail-settings/search-settings"
import type { MailSettingsSearchEntry } from "@/lib/mail-settings/settings-search-index"
import { cn } from "@/lib/utils"

export function MailSettingsSearchBar({ className }: { className?: string }) {
  const router = useRouter()
  const containerRef = useRef<HTMLDivElement>(null)
  const inputRef = useRef<HTMLInputElement>(null)
  const [query, setQuery] = useState("")
  const [focused, setFocused] = useState(false)
  const [open, setOpen] = useState(false)
  const [selectedIndex, setSelectedIndex] = useState(-1)

  const suggestions = useMemo(
    () => searchMailSettings(query),
    [query]
  )

  const showDropdown =
    open && focused && query.trim().length > 0 && suggestions.length > 0

  const navigateTo = useCallback(
    (entry: MailSettingsSearchEntry) => {
      router.push(entry.href)
      setOpen(false)
      setQuery("")
      setSelectedIndex(-1)
      inputRef.current?.blur()
    },
    [router]
  )

  const handleKeyDown = useCallback(
    (e: KeyboardEvent<HTMLInputElement>) => {
      if (!showDropdown && e.key !== "Escape") return

      switch (e.key) {
        case "ArrowDown":
          e.preventDefault()
          setSelectedIndex((i) =>
            i < suggestions.length - 1 ? i + 1 : 0
          )
          break
        case "ArrowUp":
          e.preventDefault()
          setSelectedIndex((i) =>
            i > 0 ? i - 1 : suggestions.length - 1
          )
          break
        case "Enter":
          e.preventDefault()
          if (selectedIndex >= 0 && suggestions[selectedIndex]) {
            navigateTo(suggestions[selectedIndex])
          } else if (suggestions[0]) {
            navigateTo(suggestions[0])
          }
          break
        case "Escape":
          e.preventDefault()
          setOpen(false)
          setSelectedIndex(-1)
          inputRef.current?.blur()
          break
      }
    },
    [showDropdown, selectedIndex, suggestions, navigateTo]
  )

  useEffect(() => {
    setSelectedIndex(suggestions.length > 0 ? 0 : -1)
  }, [query, suggestions.length])

  useEffect(() => {
    function handleClickOutside(event: MouseEvent) {
      if (!containerRef.current?.contains(event.target as Node)) {
        setOpen(false)
      }
    }
    document.addEventListener("mousedown", handleClickOutside)
    return () => document.removeEventListener("mousedown", handleClickOutside)
  }, [])

  return (
    <div
      ref={containerRef}
      data-mail-settings-search
      className={cn(
        "relative flex w-full min-w-0 flex-col overflow-visible",
        className
      )}
    >
      <div
        className={cn(
          DRIVE_SEARCH_INPUT_WRAP_CLASS,
          "text-[#5f6368] dark:text-[#9aa0a6]",
          focused && "shadow-md ring-1 ring-gray-300 dark:ring-gray-600"
        )}
      >
        <div className="pointer-events-none absolute left-3.5 flex items-center">
          <Search className="size-5 shrink-0" />
        </div>
        <input
          ref={inputRef}
          type="search"
          value={query}
          onChange={(e) => {
            setQuery(e.target.value)
            setOpen(true)
          }}
          onFocus={() => {
            setFocused(true)
            if (query.trim()) setOpen(true)
          }}
          onBlur={() => setFocused(false)}
          onKeyDown={handleKeyDown}
          placeholder="Rechercher dans les réglages"
          className={cn(
            "h-full w-full rounded-full border-0 bg-transparent text-sm text-foreground outline-none placeholder:text-muted-foreground",
            query ? "pl-11 pr-12" : "pl-11 pr-4"
          )}
          role="combobox"
          aria-expanded={showDropdown}
          aria-controls="mail-settings-search-listbox"
          aria-autocomplete="list"
          autoComplete="off"
        />
        {query ? (
          <Button
            type="button"
            variant="ghost"
            size="icon"
            className="absolute right-2 shrink-0 rounded-full text-muted-foreground hover:text-foreground"
            aria-label="Effacer la recherche"
            onMouseDown={(e) => e.preventDefault()}
            onClick={() => {
              setQuery("")
              setOpen(false)
              inputRef.current?.focus()
            }}
          >
            <X className="size-4" />
          </Button>
        ) : null}
      </div>

      {showDropdown ? (
        <ul
          id="mail-settings-search-listbox"
          role="listbox"
          className={cn(
            "absolute left-0 right-0 top-[calc(100%+4px)] z-50 overflow-hidden rounded-2xl py-1",
            MAIL_SEARCH_SUGGESTIONS_DROPDOWN_CLASS
          )}
        >
          {suggestions.map((entry, index) => {
            const selected = index === selectedIndex
            return (
              <li key={entry.id} role="presentation">
                <button
                  type="button"
                  role="option"
                  aria-selected={selected}
                  className={cn(
                    "flex w-full items-start gap-3 px-4 py-2.5 text-left text-sm transition-colors",
                    selected
                      ? "bg-accent text-accent-foreground"
                      : "hover:bg-accent/60"
                  )}
                  onMouseDown={(e) => e.preventDefault()}
                  onClick={() => navigateTo(entry)}
                  onMouseEnter={() => setSelectedIndex(index)}
                >
                  <div className="min-w-0 flex-1">
                    <div className="truncate font-medium text-foreground">
                      {entry.label}
                    </div>
                    <div className="truncate text-xs text-muted-foreground">
                      {entry.sectionLabel}
                      {entry.description ? ` · ${entry.description}` : null}
                    </div>
                  </div>
                </button>
              </li>
            )
          })}
        </ul>
      ) : null}
    </div>
  )
}
