'use client';

import { useState, useRef, useEffect, useMemo } from 'react';
import { useAuth } from '@/contexts/AuthContext';
import { usePathname, useRouter } from 'next/navigation';
import Link from 'next/link';
import {
  Loader2,
  MessageSquare,
  Mic,
  MicOff,
  PhoneCall,
  Send,
  Sparkles,
} from 'lucide-react';
import { useVapi } from '@/hooks/useVapi';
import toast from 'react-hot-toast';

interface Message {
  role: 'user' | 'assistant';
  content: string;
}

export default function Chat() {
  const { user, isLoading: authLoading } = useAuth();
  const router = useRouter();
  const pathname = usePathname();

  const [messages, setMessages] = useState<Message[]>([]);
  const [input, setInput] = useState('');
  const [isSending, setIsSending] = useState(false);
  const [permissionError, setPermissionError] = useState<string | null>(null);

  // Voice state
  const [isListening, setIsListening] = useState(false);
  const recognitionRef = useRef<any>(null);

  const messagesEndRef = useRef<HTMLDivElement>(null);

  const { status, error: callError, durationSeconds, callStats, startCall, endCall } =
    useVapi();

  // Redirect if not logged in
  useEffect(() => {
    if (!authLoading && !user) {
      router.push('/login');
    }
  }, [user, authLoading, router]);

  // Auto-scroll
  useEffect(() => {
    messagesEndRef.current?.scrollIntoView({ behavior: 'smooth' });
  }, [messages]);

  // Init speech recognition (client only)
  useEffect(() => {
    if (typeof window === 'undefined') return;

    const SpeechRecognition =
      (window as any).SpeechRecognition || (window as any).webkitSpeechRecognition;

    if (!SpeechRecognition) {
      console.warn('Speech recognition not supported in this browser');
      return;
    }

    const recognition = new SpeechRecognition();
    recognition.lang = 'en-US'; // change to 'es-ES' etc if you want
    recognition.continuous = false;
    recognition.interimResults = true;

    recognition.onresult = (event: SpeechRecognitionEvent) => {
      let finalText = '';
      let interimText = '';

      for (let i = event.resultIndex; i < event.results.length; i++) {
        const result = event.results[i];
        if (result.isFinal) {
          finalText += result[0].transcript;
        } else {
          interimText += result[0].transcript;
        }
      }

      // show interim in input while speaking
      if (interimText) {
        setInput(interimText);
      }

      if (finalText) {
        const cleaned = finalText.trim();
        setInput(cleaned);
        // If you want auto-send after speech, uncomment:
        // if (cleaned) {
        //   handleVoiceSend(cleaned);
        // }
      }
    };

    recognition.onerror = (event: any) => {
      console.error('Speech recognition error', event.error);
      setIsListening(false);
    };

    recognition.onend = () => {
      setIsListening(false);
    };

    recognitionRef.current = recognition;

    return () => {
      try {
        recognition.stop();
      } catch {
        // ignore
      }
      recognitionRef.current = null;
    };
  }, []);

  const sendMessage = async (
    e?: React.FormEvent,
    overrideText?: string,
  ) => {
    if (e) e.preventDefault();

    const textToSend = overrideText ?? input;
    if (!textToSend.trim() || isSending) return;

    const userMessage: Message = { role: 'user', content: textToSend };
    const updatedMessages = [...messages, userMessage];
    setMessages(updatedMessages);
    setInput('');
    setIsSending(true);

    try {
      const response = await fetch('/api/chat', {
        method: 'POST',
        headers: {
          'Content-Type': 'application/json',
        },
        body: JSON.stringify({
          messages: updatedMessages,
        }),
      });

      if (!response.ok) {
        throw new Error('Failed to get response');
      }

      const data = await response.json();

      if (data.error) {
        throw new Error(data.error);
      }

      setMessages([
        ...updatedMessages,
        { role: 'assistant', content: data.text },
      ]);
    } catch (error) {
      console.error('Error sending message:', error);
      setMessages([
        ...updatedMessages,
        {
          role: 'assistant',
          content:
            'Sorry, I encountered an error. Please try again.',
        },
      ]);
      toast.error('Unable to send your message.');
    } finally {
      setIsSending(false);
    }
  };

  // Manual send from voice text (if you want to click after dictation)
  const handleVoiceSend = (text: string) => {
    sendMessage(undefined, text);
  };

  const toggleListening = () => {
    const recognition = recognitionRef.current;
    if (!recognition) {
      console.warn('No recognition instance; browser may not support it');
      return;
    }

    if (!isListening) {
      setInput('');
      setIsListening(true);
      try {
        recognition.start();
      } catch (err) {
        console.error('Error starting recognition', err);
        setIsListening(false);
      }
    } else {
      try {
        recognition.stop();
      } catch (err) {
        console.error('Error stopping recognition', err);
      }
      setIsListening(false);
    }
  };

  const formatDuration = (seconds: number) => {
    const mins = Math.floor(seconds / 60);
    const secs = seconds % 60;
    return `${mins}m ${secs.toString().padStart(2, '0')}s`;
  };

  const callStatusLabel = useMemo(() => {
    if (status === 'connecting') return 'Connecting...';
    if (status === 'active') return 'On Call';
    if (status === 'ended') return 'Call Ended';
    if (status === 'error') return 'Error';
    return 'Ready to Call';
  }, [status]);

  const handleVoiceCall = async () => {
    setPermissionError(null);

    if (status === 'active' || status === 'connecting') {
      await endCall();
      return;
    }

    try {
      await navigator.mediaDevices.getUserMedia({ audio: true });
    } catch (error) {
      console.error('Microphone permission denied', error);
      setPermissionError(
        'Microphone access is required. Please allow permission and use a modern browser.'
      );
      toast.error('Microphone access is required to start a call.');
      return;
    }

    try {
      await startCall();
      toast.success('Call started.');
    } catch (error) {
      console.error('Unable to start call', error);
      toast.error('Unable to start the call.');
    }
  };

  if (authLoading) {
    return (
      <div className="min-h-screen bg-gradient-to-br from-[#0f0b1a] via-[#1b1330] to-[#0f1b3d] flex items-center justify-center">
        <div className="text-white text-xl animate-pulse">Loading...</div>
      </div>
    );
  }

  if (!user) {
    return null;
  }

  const navLinks = [
    { label: 'Dashboard', href: '/dashboard' },
    { label: 'Scheduled Calls', href: '/dashboard/scheduled-calls' },
    { label: 'Voice Agent', href: '/dashboard/agent-settings' },
    { label: 'Credits', href: '/dashboard/credits' },
    { label: 'Notifications', href: '/dashboard/notifications' },
  ];

  return (
    <div className="min-h-screen bg-gradient-to-br from-[#0f0b1a] via-[#1b1330] to-[#0f1b3d] text-white">
      <nav className="border-b border-white/10 bg-white/5 backdrop-blur-sm">
        <div className="max-w-5xl mx-auto px-6 py-4 flex flex-wrap items-center justify-between gap-4">
          <div className="flex items-center gap-3">
            <div className="h-10 w-10 rounded-2xl bg-[#8b5cf6]/20 border border-[#8b5cf6]/40 flex items-center justify-center">
              <MessageSquare className="h-5 w-5 text-[#8b5cf6]" />
            </div>
            <div>
              <h1 className="text-2xl font-semibold">Chat</h1>
              <p className="text-xs text-[#9ca3af]">Talk to HolaCompi in real time</p>
            </div>
          </div>
          <div className="flex flex-wrap gap-2">
            {navLinks.map((link) => {
              const isActive = pathname === link.href;
              return (
                <Link
                  key={link.href}
                  href={link.href}
                  className={`px-3 py-1.5 rounded-full border text-xs transition ${
                    isActive
                      ? 'bg-[#8b5cf6]/20 border-[#8b5cf6]/40 text-white'
                      : 'bg-white/5 border-white/10 text-[#9ca3af] hover:text-white'
                  }`}
                >
                  {link.label}
                </Link>
              );
            })}
          </div>
        </div>
      </nav>

      <div className="max-w-5xl mx-auto px-6 py-8">
        <div className="bg-[#1a1625] rounded-3xl border border-[#8b5cf6]/20 p-6 shadow-2xl h-[70vh] flex flex-col">
          <div className="mb-4 rounded-2xl border border-white/10 bg-white/5 backdrop-blur-xl p-4 flex flex-col gap-3">
            <div className="flex flex-wrap items-center justify-between gap-3">
              <div className="flex items-center gap-3">
                <div
                  className={`h-10 w-10 rounded-2xl flex items-center justify-center border ${
                    status === 'active'
                      ? 'bg-red-500/20 border-red-400/40'
                      : 'bg-[#8b5cf6]/20 border-[#8b5cf6]/40'
                  }`}
                >
                  <PhoneCall
                    className={`h-5 w-5 ${
                      status === 'active' ? 'text-red-300' : 'text-[#8b5cf6]'
                    }`}
                  />
                </div>
                <div>
                  <p className="text-sm font-semibold">{callStatusLabel}</p>
                  <div className="text-xs text-[#9ca3af] flex items-center gap-2">
                    {status === 'connecting' && (
                      <>
                        <Loader2 className="h-3 w-3 animate-spin" />
                        Connecting to Vapi...
                      </>
                    )}
                    {status === 'active' && (
                      <>
                        <span className="h-2 w-2 rounded-full bg-red-400 animate-pulse" />
                        Duration: {formatDuration(durationSeconds)}
                      </>
                    )}
                    {status === 'idle' && 'Tap start to begin a voice call'}
                  </div>
                </div>
              </div>

              <button
                onClick={handleVoiceCall}
                disabled={status === 'connecting'}
                className={`px-5 py-3 rounded-2xl font-semibold shadow-2xl transition flex items-center gap-2 ${
                  status === 'active'
                    ? 'bg-red-500 text-white hover:bg-red-600'
                    : 'bg-gradient-to-r from-[#8b5cf6] to-[#4f46e5] text-white hover:from-[#7c3aed] hover:to-[#4338ca]'
                } ${status === 'connecting' ? 'opacity-60 cursor-not-allowed' : ''}`}
              >
                <Mic className="h-4 w-4" />
                {status === 'active'
                  ? 'End Call'
                  : status === 'connecting'
                  ? 'Connecting...'
                  : 'Start Call'}
              </button>
            </div>

            {(permissionError || callError) && (
              <div className="text-xs text-red-300">
                {permissionError || callError}
              </div>
            )}

            {status === 'ended' && callStats && (
              <div className="rounded-2xl border border-white/10 bg-[#0f0b1a]/60 p-4">
                <p className="text-sm font-semibold">Call Summary</p>
                <div className="mt-2 grid grid-cols-1 sm:grid-cols-3 gap-3 text-xs text-[#9ca3af]">
                  <div>
                    <p className="uppercase">Duration</p>
                    <p className="text-white">{formatDuration(callStats.durationSeconds)}</p>
                  </div>
                  <div>
                    <p className="uppercase">Credits Used</p>
                    <p className="text-white">{callStats.creditsUsed}</p>
                  </div>
                  <div>
                    <p className="uppercase">Transcript</p>
                    <button className="text-[#8b5cf6] hover:text-white transition">
                      View Transcript
                    </button>
                  </div>
                </div>
              </div>
            )}
          </div>
          <div className="flex-1 overflow-y-auto mb-4 space-y-4">
            {messages.length === 0 && (
              <div className="text-[#9ca3af] text-center mt-20">
                Start a conversation with your AI companion
              </div>
            )}

            {messages.map((message, index) => (
              <div
                key={index}
                className={`flex ${
                  message.role === 'user'
                    ? 'justify-end'
                    : 'justify-start'
                }`}
              >
                <div
                  className={`max-w-[70%] rounded-2xl p-4 shadow ${
                    message.role === 'user'
                      ? 'bg-[#8b5cf6] text-white'
                      : 'bg-[#0f0b1a] border border-white/10 text-white'
                  }`}
                >
                  <p className="whitespace-pre-wrap">
                    {message.content}
                  </p>
                </div>
              </div>
            ))}

            {isSending && (
              <div className="flex justify-start">
                <div className="bg-[#0f0b1a] border border-white/10 rounded-2xl p-4">
                  <div className="flex space-x-2">
                    <div className="w-2 h-2 bg-[#9ca3af] rounded-full animate-bounce"></div>
                    <div
                      className="w-2 h-2 bg-[#9ca3af] rounded-full animate-bounce"
                      style={{ animationDelay: '0.1s' }}
                    ></div>
                    <div
                      className="w-2 h-2 bg-[#9ca3af] rounded-full animate-bounce"
                      style={{ animationDelay: '0.2s' }}
                    ></div>
                  </div>
                </div>
              </div>
            )}

            <div ref={messagesEndRef} />
          </div>

          <form onSubmit={(e) => sendMessage(e)} className="flex gap-2 items-center">
            <div className="flex-1 flex items-center gap-2 bg-[#0f0b1a] border border-white/10 rounded-2xl px-4 py-3 focus-within:ring-2 focus-within:ring-[#8b5cf6] transition">
              <Sparkles className="h-4 w-4 text-[#8b5cf6]" />
              <input
                type="text"
                value={input}
                onChange={(e) => setInput(e.target.value)}
                placeholder={isListening ? 'Listening...' : 'Type your message...'}
                className="flex-1 bg-transparent text-white placeholder:text-[#9ca3af] focus:outline-none"
                disabled={isSending}
              />
            </div>

            <button
              type="button"
              onClick={toggleListening}
              className={`px-4 py-3 rounded-2xl font-semibold transition flex items-center gap-2 ${
                isListening
                  ? 'bg-red-500/80 hover:bg-red-500 text-white'
                  : 'bg-white/5 border border-white/10 text-[#9ca3af] hover:text-white'
              }`}
            >
              {isListening ? <MicOff className="h-4 w-4" /> : <Mic className="h-4 w-4" />}
            </button>

            <button
              type="submit"
              disabled={isSending || !input.trim()}
              className="bg-[#8b5cf6] hover:bg-[#7c3aed] disabled:bg-white/10 disabled:text-[#9ca3af] disabled:cursor-not-allowed px-6 py-3 rounded-2xl font-semibold transition flex items-center gap-2"
            >
              <Send className="h-4 w-4" />
              Send
            </button>
          </form>
        </div>
      </div>
    </div>
  );
}
