import { Controller } from "@hotwired/stimulus"
import { Picker } from "emoji-mart"

// Emoji Picker Controller
// Based on RailsBlocks pattern: https://railsblocks.com/docs/emoji-picker
export default class extends Controller {
  static targets = ["input", "button", "pickerContainer"]
  static values = {
    autoSubmit: { type: Boolean, default: true }
  }

  connect() {
    this.picker = null
    this.setupKeyboardListeners()
  }

  disconnect() {
    this.removePicker()
    this.removeKeyboardListeners()
  }

  toggle(event) {
    event.preventDefault()
    event.stopPropagation()

    if (this.pickerContainerTarget.classList.contains("hidden")) {
      this.open()
    } else {
      this.close()
    }
  }

  open() {
    if (!this.picker) {
      this.createPicker()
    }

    this.pickerContainerTarget.classList.remove("hidden")
    this.setupOutsideClickListener()
  }

  close() {
    this.pickerContainerTarget.classList.add("hidden")
    this.removeOutsideClickListener()
  }

  createPicker() {
    this.picker = new Picker({
      onEmojiSelect: this.onEmojiSelect.bind(this),
      theme: this.getTheme(),
      previewPosition: "none",
      skinTonePosition: "search",
      maxFrequentRows: 2,
      perLine: 8,
      navPosition: "bottom",
      categories: [
        "frequent",
        "people",
        "nature",
        "foods",
        "activity",
        "places",
        "objects",
        "symbols",
        "flags"
      ]
    })

    this.pickerContainerTarget.appendChild(this.picker)
  }

  onEmojiSelect(emoji) {
    if (!emoji || !emoji.native) return

    // Update input value
    this.inputTarget.value = emoji.native

    // Update button to show selected emoji
    if (this.hasButtonTarget) {
      // Find the display element (could be a span or the button itself)
      const display = this.buttonTarget.querySelector('[data-emoji-picker-display]') || this.buttonTarget
      display.textContent = emoji.native
    }

    // Close picker
    this.close()

    // Auto-submit if enabled
    if (this.autoSubmitValue) {
      this.submitForm()
    }

    // Dispatch custom event for advanced use cases
    this.dispatch("select", { detail: { emoji: emoji.native } })
  }

  submitForm() {
    const form = this.element.closest("form")
    if (form && !form.requestSubmit) {
      // Fallback for older browsers
      form.submit()
    } else if (form) {
      form.requestSubmit()
    }
  }

  clearEmoji(event) {
    event?.preventDefault()
    this.inputTarget.value = ""

    if (this.hasButtonTarget) {
      const display = this.buttonTarget.querySelector('[data-emoji-picker-display]') || this.buttonTarget
      // Reset to default emoji or icon
      const defaultIcon = this.buttonTarget.dataset.defaultIcon || "😀"
      display.textContent = defaultIcon
    }

    this.dispatch("clear")
  }

  getTheme() {
    // Detect dark mode from document
    if (document.documentElement.getAttribute('data-theme') === 'dark' ||
      document.documentElement.classList.contains('dark')) {
      return 'dark'
    }
    return 'light'
  }

  setupKeyboardListeners() {
    this.handleKeydown = this.handleKeydown.bind(this)
    document.addEventListener("keydown", this.handleKeydown)
  }

  removeKeyboardListeners() {
    document.removeEventListener("keydown", this.handleKeydown)
  }

  handleKeydown(event) {
    // Close on Escape
    if (event.key === "Escape" && !this.pickerContainerTarget.classList.contains("hidden")) {
      this.close()
    }

    // Clear on Delete/Backspace (when picker is open)
    if ((event.key === "Delete" || event.key === "Backspace") &&
      !this.pickerContainerTarget.classList.contains("hidden") &&
      event.target === this.inputTarget) {
      event.preventDefault()
      this.clearEmoji()
    }
  }

  setupOutsideClickListener() {
    this.handleOutsideClick = this.handleOutsideClick.bind(this)
    // Use setTimeout to avoid immediate triggering from the toggle click
    setTimeout(() => {
      document.addEventListener("click", this.handleOutsideClick)
    }, 0)
  }

  removeOutsideClickListener() {
    if (this.handleOutsideClick) {
      document.removeEventListener("click", this.handleOutsideClick)
    }
  }

  handleOutsideClick(event) {
    if (!this.element.contains(event.target)) {
      this.close()
    }
  }

  removePicker() {
    if (this.picker && this.picker.remove) {
      this.picker.remove()
    }
    this.picker = null
  }
}
