import { useState, useRef, useEffect } from 'react';
import { Check, Loader2, MessageCircleQuestion, SkipForward } from 'lucide-react';
import { cn } from '@/lib/utils';
import { UserPrompt, UserPromptResponse } from '../types';

interface UserPromptMessageProps {
  prompt: UserPrompt;
  onRespond: (response: UserPromptResponse, displayValue: string) => Promise<void>;
  isAnswered: boolean;
  answeredValue?: string;
}

export function UserPromptMessage({
  prompt,
  onRespond,
  isAnswered,
  answeredValue,
}: UserPromptMessageProps): React.ReactNode {
  const [selectedOptions, setSelectedOptions] = useState<Set<string>>(new Set());
  const [freeText, setFreeText] = useState('');
  const [focusedIndex, setFocusedIndex] = useState(-1);
  const [isSubmitting, setIsSubmitting] = useState(false);
  const containerRef = useRef<HTMLDivElement>(null);
  const inputRef = useRef<HTMLInputElement>(null);

  // Auto-focus the container when the prompt appears so keyboard navigation works immediately.
  useEffect(() => {
    if (!isAnswered) {
      containerRef.current?.focus();
    }
  }, [isAnswered]);

  const handleOptionClick = (optionId: string) => {
    if (isAnswered) return;

    const newSelected = new Set(selectedOptions);
    if (prompt.multi_select) {
      if (newSelected.has(optionId)) {
        newSelected.delete(optionId);
      } else {
        newSelected.add(optionId);
      }
    } else {
      if (newSelected.has(optionId)) {
        newSelected.clear();
      } else {
        newSelected.clear();
        newSelected.add(optionId);
      }
    }
    setSelectedOptions(newSelected);
    setFocusedIndex(-1);
    if (newSelected.size > 0) {
      setFreeText('');
    }
  };

  const handleFreeTextChange = (value: string) => {
    setFreeText(value);
    setFocusedIndex(-1);
    if (value) {
      setSelectedOptions(new Set());
    }
  };

  const handleSubmit = async () => {
    setIsSubmitting(true);
    try {
      const response: UserPromptResponse = {
        prompt_id: prompt.prompt_id,
      };

      let displayValue = '';
      if (selectedOptions.size > 0) {
        response.selected_option_ids = Array.from(selectedOptions);
        const selectedLabels = prompt.options
          ?.filter(opt => selectedOptions.has(opt.id))
          .map(opt => opt.label) ?? [];
        displayValue = selectedLabels.join(', ');
      }
      if (freeText) {
        response.free_text_response = freeText;
        displayValue = displayValue ? `${displayValue}; ${freeText}` : freeText;
      }

      await onRespond(response, displayValue || 'Submitted');
    } catch {
      setIsSubmitting(false);
    }
  };

  const handleSkip = async () => {
    setIsSubmitting(true);
    try {
      await onRespond({
        prompt_id: prompt.prompt_id,
        cancelled: true,
      }, 'Skipped');
    } catch {
      setIsSubmitting(false);
    }
  };

  const canSubmit = selectedOptions.size > 0 || freeText.trim().length > 0;

  const handleKeyDown = (e: React.KeyboardEvent<HTMLDivElement>) => {
    if (isAnswered) return;

    // Let focused buttons (Submit, Skip, option buttons) handle Enter/Space natively.
    if (e.target instanceof HTMLButtonElement) return;

    // Don't intercept any keys when free-text input is focused, except Enter to submit.
    if (e.target === inputRef.current) {
      if (e.key === 'Enter' && canSubmit) {
        e.preventDefault();
        handleSubmit();
      }
      return;
    }

    const optionCount = prompt.options?.length ?? 0;

    if (optionCount > 0) {
      if (e.key === 'ArrowDown' || e.key === 'ArrowRight') {
        e.preventDefault();
        setFocusedIndex(prev => Math.min(prev + 1, optionCount - 1));
        return;
      }
      if (e.key === 'ArrowUp' || e.key === 'ArrowLeft') {
        e.preventDefault();
        setFocusedIndex(prev => Math.max(prev - 1, 0));
        return;
      }
      if ((e.key === 'Enter' || e.key === ' ') && focusedIndex >= 0) {
        e.preventDefault();
        const option = prompt.options?.[focusedIndex];
        if (option) handleOptionClick(option.id);
        return;
      }
    }

    if (e.key === 'Enter' && canSubmit) {
      e.preventDefault();
      handleSubmit();
      return;
    }

    if (e.key === 'Escape') {
      e.preventDefault();
      containerRef.current?.blur();
    }
  };

  if (isAnswered) {
    return (
      <div className="pl-1">
        <div className="rounded-lg border border-green-300 dark:border-green-500/30 bg-green-50 dark:bg-green-500/5 p-2">
          <div className="flex items-start gap-1.5">
            <Check className="h-3 w-3 mt-0.5 flex-shrink-0 text-green-600 dark:text-green-400" />
            <div className="flex-1 min-w-0">
              <p className="text-xs font-medium text-foreground">{prompt.question}</p>
              <p className="text-xs text-muted-foreground mt-0.5">
                Answered: {answeredValue || 'Skipped'}
              </p>
            </div>
          </div>
        </div>
      </div>
    );
  }

  return (
    <div className="pl-1">
      <div
        ref={containerRef}
        tabIndex={0}
        onKeyDown={handleKeyDown}
        role={prompt.options && prompt.options.length > 0 ? 'listbox' : undefined}
        aria-label={prompt.question}
        aria-multiselectable={prompt.multi_select || undefined}
        aria-activedescendant={focusedIndex >= 0 && prompt.options?.[focusedIndex] ? prompt.options[focusedIndex].id : undefined}
        className="rounded-lg border border-orange-300 dark:border-amber-500/40 bg-orange-50 dark:bg-amber-500/10 p-2 outline-none"
      >
        <div className="flex items-start gap-1.5 mb-2">
          <MessageCircleQuestion className="h-3.5 w-3.5 mt-0.5 flex-shrink-0 text-orange-600 dark:text-orange-400" />
          <p className="text-xs font-medium text-foreground">{prompt.question}</p>
        </div>

        {prompt.options && prompt.options.length > 0 && (
          <div className="flex flex-wrap gap-1 mb-2">
            {prompt.options.map((option, index) => (
              <button
                key={option.id}
                id={option.id}
                role="option"
                aria-selected={selectedOptions.has(option.id)}
                onClick={() => handleOptionClick(option.id)}
                className={cn(
                  'px-2 py-1 text-xs rounded border transition-colors',
                  selectedOptions.has(option.id)
                    ? 'bg-amber-500 text-white border-amber-500'
                    : 'bg-background border-border hover:border-amber-500/50',
                  index === focusedIndex && 'ring-1 ring-amber-500/70'
                )}
                title={option.description}
              >
                {option.label}
              </button>
            ))}
          </div>
        )}

        {prompt.allow_free_text && (
          <input
            ref={inputRef}
            type="text"
            value={freeText}
            onChange={(e) => handleFreeTextChange(e.target.value)}
            placeholder={prompt.free_text_placeholder || 'Or type your answer...'}
            className="w-full px-2 py-1 text-xs rounded border border-border bg-background focus:outline-none focus:border-amber-500/50 mb-2"
          />
        )}

        <div className="flex gap-1">
          <button
            onClick={handleSubmit}
            disabled={!canSubmit || isSubmitting}
            className={cn(
              'px-2 py-1 text-xs rounded transition-colors font-medium flex items-center gap-1',
              canSubmit && !isSubmitting
                ? 'bg-amber-600 text-white hover:bg-amber-700 dark:bg-amber-500 dark:text-black dark:hover:bg-amber-400'
                : 'bg-muted text-muted-foreground cursor-not-allowed'
            )}
          >
            {isSubmitting && <Loader2 className="h-3 w-3 animate-spin" />}
            {isSubmitting ? 'Sending...' : 'Submit'}
          </button>
          <button
            onClick={handleSkip}
            disabled={isSubmitting}
            className={cn(
              'px-2 py-1 text-xs rounded border border-border transition-colors flex items-center gap-1',
              isSubmitting ? 'opacity-50 cursor-not-allowed' : 'hover:bg-muted'
            )}
          >
            <SkipForward className="h-3 w-3" />
            Skip
          </button>
        </div>
      </div>
    </div>
  );
}
