import React, { useState, useRef, useEffect, useCallback } from 'react'
import { createPortal } from 'react-dom'
import EmojiMartPicker from '../common/EmojiMartPicker'
import extractNativeEmoji from '../common/extractNativeEmoji'
import isEventWithinNode from '../common/isEventWithinNode'
import loadEmojiMartData from '../common/loadEmojiMartData'

/**
 * Emoji picker button for the forum rich-text editor.
 * Uses the same emoji-mart picker as profile tweets / comments
 * so the UI is consistent across the whole site.
 *
 * The panel is rendered through a React portal so it escapes any
 * overflow-hidden containers (like the editor wrapper).
 */
export default function EmojiPicker({ onSelect, editor }) {
  const [open, setOpen] = useState(false)
  const [pickerData, setPickerData] = useState(null)
  const [panelStyle, setPanelStyle] = useState({})
  const panelRef = useRef(null)
  const buttonRef = useRef(null)

  useEffect(() => {
    if (!open || pickerData) return

    let cancelled = false

    loadEmojiMartData().then((data) => {
      if (!cancelled) {
        setPickerData(data)
      }
    })

    return () => {
      cancelled = true
    }
  }, [open, pickerData])

  // Position the portal panel relative to the trigger button
  useEffect(() => {
    if (!open || !buttonRef.current) return
    const rect = buttonRef.current.getBoundingClientRect()
    const panelWidth = 352   // emoji-mart default width
    const panelHeight = 435  // approximate picker height

    const spaceAbove = rect.top
    const openAbove = spaceAbove > panelHeight + 8

    setPanelStyle({
      position: 'fixed',
      zIndex: 9999,
      left: Math.max(8, Math.min(rect.right - panelWidth, window.innerWidth - panelWidth - 8)),
      ...(openAbove
        ? { bottom: window.innerHeight - rect.top + 6 }
        : { top: rect.bottom + 6 }),
    })
  }, [open])

  // Close on outside click
  useEffect(() => {
    if (!open) return
    const handler = (e) => {
      if (!isEventWithinNode(e, panelRef.current) && !isEventWithinNode(e, buttonRef.current)) {
        setOpen(false)
      }
    }
    document.addEventListener('mousedown', handler)
    return () => document.removeEventListener('mousedown', handler)
  }, [open])

  // Close on Escape
  useEffect(() => {
    if (!open) return
    const handler = (e) => { if (e.key === 'Escape') setOpen(false) }
    document.addEventListener('keydown', handler)
    return () => document.removeEventListener('keydown', handler)
  }, [open])

  const handleSelect = useCallback((emoji) => {
    const native = extractNativeEmoji(emoji)
    if (!native) {
      setOpen(false)
      return
    }

    onSelect?.(native)
    if (editor) {
      editor.chain().focus().insertContent(native).run()
    }
    setOpen(false)
  }, [onSelect, editor])

  const panel = open ? createPortal(
    <div
      ref={panelRef}
      style={panelStyle}
      className="rounded-xl shadow-2xl overflow-hidden"
    >
      {pickerData ? (
        <EmojiMartPicker
          data={pickerData}
          onEmojiSelect={handleSelect}
          theme="dark"
          previewPosition="none"
          skinTonePosition="search"
          maxFrequentRows={2}
          perLine={9}
        />
      ) : (
        <div className="flex h-24 w-[352px] items-center justify-center bg-zinc-900 px-4 text-sm text-zinc-300">
          Loading emojis...
        </div>
      )}
    </div>,
    document.body,
  ) : null

  return (
    <div className="relative">
      <button
        ref={buttonRef}
        type="button"
        onClick={() => setOpen((v) => !v)}
        title="Insert emoji"
        aria-label="Open emoji picker"
        aria-expanded={open}
        className={[
          'inline-flex h-8 w-8 items-center justify-center rounded-lg text-sm transition-colors',
          'focus:outline-none focus-visible:ring-2 focus-visible:ring-sky-400',
          open
            ? 'bg-sky-600/25 text-sky-300'
            : 'text-zinc-400 hover:bg-white/[0.06] hover:text-zinc-200',
        ].join(' ')}
      >
        <span className="text-[15px]">😊</span>
      </button>
      {panel}
    </div>
  )
}
