/**
 * useKeyboardNavigation Hook
 * Provides keyboard navigation for alerts
 */

import { useEffect, useCallback, useRef, useState } from 'react';

export interface KeyboardNavigationCallbacks {
  onMoveUp: () => void;
  onMoveDown: () => void;
  onSelect: () => void;
  onExpand: () => void;
  onMarkAsRead: () => void;
  onDismiss: () => void;
  onSnooze: () => void;
  onEscape: () => void;
  onSelectAll: () => void;
  onSearch: () => void;
}

export interface UseKeyboardNavigationReturn {
  focusedIndex: number;
  setFocusedIndex: (index: number) => void;
  handleKeyDown: (event: React.KeyboardEvent) => void;
}

/**
 * Hook to enable keyboard navigation for alerts
 */
export function useKeyboardNavigation(
  itemCount: number,
  callbacks: KeyboardNavigationCallbacks,
  enabled: boolean = true
): UseKeyboardNavigationReturn {
  const [focusedIndex, setFocusedIndex] = useState(0);
  const callbacksRef = useRef(callbacks);

  // Update callbacks ref when they change
  useEffect(() => {
    callbacksRef.current = callbacks;
  }, [callbacks]);

  // Reset focused index when item count changes
  useEffect(() => {
    if (focusedIndex >= itemCount && itemCount > 0) {
      setFocusedIndex(Math.max(0, itemCount - 1));
    }
  }, [itemCount, focusedIndex]);

  const handleKeyDown = useCallback((event: React.KeyboardEvent | KeyboardEvent) => {
    if (!enabled || itemCount === 0) {
      return;
    }

    const cbs = callbacksRef.current;

    switch (event.key) {
      case 'ArrowUp':
        event.preventDefault();
        setFocusedIndex(prev => Math.max(0, prev - 1));
        cbs.onMoveUp();
        break;

      case 'ArrowDown':
        event.preventDefault();
        setFocusedIndex(prev => Math.min(itemCount - 1, prev + 1));
        cbs.onMoveDown();
        break;

      case 'Enter':
        event.preventDefault();
        cbs.onExpand();
        break;

      case ' ':
        event.preventDefault();
        cbs.onSelect();
        break;

      case 'r':
        if (!event.ctrlKey && !event.metaKey) {
          event.preventDefault();
          cbs.onMarkAsRead();
        }
        break;

      case 'd':
        if (!event.ctrlKey && !event.metaKey) {
          event.preventDefault();
          cbs.onDismiss();
        }
        break;

      case 's':
        if (!event.ctrlKey && !event.metaKey) {
          event.preventDefault();
          cbs.onSnooze();
        }
        break;

      case 'Escape':
        event.preventDefault();
        cbs.onEscape();
        break;

      case 'a':
        if (event.ctrlKey || event.metaKey) {
          event.preventDefault();
          cbs.onSelectAll();
        }
        break;

      case '/':
        if (!event.ctrlKey && !event.metaKey) {
          event.preventDefault();
          cbs.onSearch();
        }
        break;

      default:
        break;
    }
  }, [enabled, itemCount]);

  // Add global keyboard listener
  useEffect(() => {
    if (!enabled) {
      return;
    }

    const handleGlobalKeyDown = (event: KeyboardEvent) => {
      // Only handle if no input is focused
      const target = event.target as HTMLElement;
      if (target.tagName === 'INPUT' || target.tagName === 'TEXTAREA' || target.isContentEditable) {
        return;
      }

      handleKeyDown(event);
    };

    window.addEventListener('keydown', handleGlobalKeyDown);

    return () => {
      window.removeEventListener('keydown', handleGlobalKeyDown);
    };
  }, [enabled, handleKeyDown]);

  return {
    focusedIndex,
    setFocusedIndex,
    handleKeyDown,
  };
}
