'use client'

import type { ControlAvailability, ControlTooltip } from '../control-options'
import type { UseHeadingDropdownMenuConfig } from '@admin/hooks/content-editor/use-heading-dropdown-menu'
import { Button } from '@admin/components/ui/button'
import {
  DropdownMenu,
  DropdownMenuContent,
  DropdownMenuGroup,
  DropdownMenuTrigger
} from '@admin/components/ui/dropdown-menu'
import { useHeadingDropdownMenu } from '@admin/hooks/content-editor/use-heading-dropdown-menu'
import { useTiptapEditor } from '@admin/hooks/content-editor/use-tiptap-editor'
import { ChevronDownIcon } from 'lucide-react'
import { useCallback, useState } from 'react'
import { getControlTooltipTitle, shouldHideUnavailableControl } from '../control-options'
import { HeadingDropdownMenuItem } from './heading-dropdown-menu-item'

type EditorButtonProps = React.ComponentProps<typeof Button> & {
  tooltip?: ControlTooltip
}

export interface HeadingDropdownMenuProps
  extends
    Omit<EditorButtonProps, 'type'>,
    Omit<UseHeadingDropdownMenuConfig, 'hideWhenUnavailable'> {
  availability?: ControlAvailability
  onOpenChange?: (isOpen: boolean) => void
}

export function HeadingDropdownMenu({
  editor: providedEditor,
  availability,
  levels = [2, 3, 4, 5, 6],
  onOpenChange,
  tooltip,
  children,
  ref,
  ...buttonProps
}: HeadingDropdownMenuProps) {
  const { editor } = useTiptapEditor(providedEditor)
  const [isOpen, setIsOpen] = useState<boolean>(false)
  const { isVisible, isActive, canToggle, Icon } = useHeadingDropdownMenu({
    editor,
    levels,
    hideWhenUnavailable: shouldHideUnavailableControl(availability)
  })

  const handleOpenChange = useCallback(
    (open: boolean) => {
      if (!editor || !canToggle) return
      setIsOpen(open)
      onOpenChange?.(open)
    },
    [canToggle, editor, onOpenChange]
  )

  if (!isVisible) {
    return null
  }

  return (
    <DropdownMenu modal={false} open={isOpen} onOpenChange={handleOpenChange}>
      <DropdownMenuTrigger
        render={
          <Button
            type="button"
            variant="ghost"
            data-active-state={isActive ? 'on' : 'off'}
            role="button"
            tabIndex={-1}
            disabled={!canToggle}
            data-disabled={!canToggle}
            aria-label="Format text as heading"
            aria-pressed={isActive}
            title={getControlTooltipTitle(tooltip, 'Heading')}
            size="icon-sm"
            className="w-auto px-2"
            {...buttonProps}
            ref={ref}
            onPointerDown={(event) => event.preventDefault()}
            onClick={() => handleOpenChange(!isOpen)}
          >
            {children ? (
              children
            ) : (
              <>
                <Icon />
                <ChevronDownIcon className="tiptap-button-dropdown-small" />
              </>
            )}
          </Button>
        }
      ></DropdownMenuTrigger>

      <DropdownMenuContent
        align="start"
        className="w-auto min-w-40"
        finalFocus={false}
        portalled={false}
      >
        <DropdownMenuGroup>
          {levels.map((level) => (
            <HeadingDropdownMenuItem key={`heading-${level}`} editor={editor} level={level} />
          ))}
        </DropdownMenuGroup>
      </DropdownMenuContent>
    </DropdownMenu>
  )
}

export default HeadingDropdownMenu
