import { ref, onMounted, onBeforeUnmount, nextTick } from 'vue'

/**
 * Provides keyboard navigation for a list of items using arrow keys.
 *
 * @param {import('vue').Ref<number>} itemCount - Ref holding the number of items in the list
 * @param {Function} onSelect - Callback when Enter is pressed on a focused item (receives index)
 * @returns {{ focusedIndex: import('vue').Ref<number>, onKeydown: Function, focusItem: Function }}
 */
export function useListNavigation(itemCount, onSelect) {
  const focusedIndex = ref(-1)

  function focusItem(index) {
    focusedIndex.value = Math.max(0, Math.min(index, itemCount.value - 1))
    nextTick(() => {
      const el = document.querySelector(`[data-list-index="${focusedIndex.value}"]`)
      el?.focus()
    })
  }

  function onKeydown(event) {
    const tag = event.target.tagName.toLowerCase()
    if (tag === 'input' || tag === 'textarea' || tag === 'select') return

    if (event.key === 'ArrowDown') {
      event.preventDefault()
      if (focusedIndex.value < 0) {
        focusItem(0)
      } else {
        focusItem(focusedIndex.value + 1)
      }
    } else if (event.key === 'ArrowUp') {
      event.preventDefault()
      if (focusedIndex.value > 0) {
        focusItem(focusedIndex.value - 1)
      }
    } else if (event.key === 'Enter' && focusedIndex.value >= 0) {
      event.preventDefault()
      onSelect(focusedIndex.value)
    } else if (event.key === 'Escape' && focusedIndex.value >= 0) {
      event.preventDefault()
      focusedIndex.value = -1
    }
  }

  onMounted(() => {
    window.addEventListener('keydown', onKeydown)
  })

  onBeforeUnmount(() => {
    window.removeEventListener('keydown', onKeydown)
  })

  return { focusedIndex, onKeydown, focusItem }
}
