'use client' import React, { useState, useRef, useEffect } from 'react' import Window from './Window' import ReactMarkdown from 'react-markdown' import remarkGfm from 'remark-gfm' import rehypeHighlight from 'rehype-highlight' import { PaperPlaneRight, Sparkle, ArrowUp } from '@phosphor-icons/react' interface GeminiChatProps { onClose: () => void onMinimize?: () => void onMaximize?: () => void onFocus?: () => void zIndex?: number } interface Message { id: string role: 'user' | 'assistant' content: string thought?: string timestamp: number } export function GeminiChat({ onClose, onMinimize, onMaximize, onFocus, zIndex }: GeminiChatProps) { const [messages, setMessages] = useState([ { id: '1', role: 'assistant', content: "Hello! I'm Gemini. How can I help you today?", timestamp: Date.now() } ]) const [input, setInput] = useState('') const [isLoading, setIsLoading] = useState(false) const scrollRef = useRef(null) const inputRef = useRef(null) useEffect(() => { // Load messages from localStorage const savedMessages = localStorage.getItem('gemini-chat-messages') if (savedMessages) { try { const parsed = JSON.parse(savedMessages) if (parsed.length > 0) { setMessages(parsed) } } catch (e) { console.error('Failed to load messages') } } }, []) useEffect(() => { // Save messages to localStorage if (messages.length > 1) { localStorage.setItem('gemini-chat-messages', JSON.stringify(messages.slice(-20))) // Keep last 20 messages } }, [messages]) useEffect(() => { if (scrollRef.current) { scrollRef.current.scrollTop = scrollRef.current.scrollHeight } }, [messages]) const handleSend = async () => { if (!input.trim() || isLoading) return const userMessage: Message = { id: Date.now().toString(), role: 'user', content: input.trim(), timestamp: Date.now() } setMessages(prev => [...prev, userMessage]) setInput('') setIsLoading(true) try { // Get conversation history (last 10 messages) const history = messages.slice(-10).map(msg => ({ role: msg.role, content: msg.content })) const response = await fetch('/api/gemini/chat', { method: 'POST', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify({ message: userMessage.content, history }), }) if (!response.ok) throw new Error('Network response was not ok') const reader = response.body?.getReader() const decoder = new TextDecoder() // Create a placeholder message const assistantMessage: Message = { id: (Date.now() + 1).toString(), role: 'assistant', content: '', thought: '', timestamp: Date.now() } setMessages(prev => [...prev, assistantMessage]) if (reader) { while (true) { const { done, value } = await reader.read() if (done) break const chunk = decoder.decode(value, { stream: true }) const lines = chunk.split('\n\n') for (const line of lines) { if (line.startsWith('data: ')) { try { const data = JSON.parse(line.slice(6)) setMessages(prev => { const newMessages = [...prev] const lastMsg = newMessages[newMessages.length - 1] if (lastMsg.id === assistantMessage.id) { return [ ...newMessages.slice(0, -1), { ...lastMsg, content: lastMsg.content + (data.text || ''), thought: (lastMsg.thought || '') + (data.thought || '') } ] } return newMessages }) } catch (e) { console.error('Error parsing chunk:', e) } } } } } } catch (error) { console.error('Error sending message:', error) const errorMessage: Message = { id: (Date.now() + 1).toString(), role: 'assistant', content: "I'm currently running in demo mode. For full functionality, please ensure the API is configured.", timestamp: Date.now() } setMessages(prev => [...prev, errorMessage]) } setIsLoading(false) } const handleKeyPress = (e: React.KeyboardEvent) => { if (e.key === 'Enter' && !e.shiftKey) { e.preventDefault() handleSend() } } const clearChat = () => { setMessages([ { id: Date.now().toString(), role: 'assistant', content: "Chat history cleared. How can I help you today?", timestamp: Date.now() } ]) localStorage.removeItem('gemini-chat-messages') } return (
{/* Chat Header */}
Gemini
{/* Messages Area */}
{messages.map(message => (
{message.role === 'assistant' && (

Gemini

)} {message.thought && (
Thinking Process:
{message.thought}
)}
{message.content}
))} {isLoading && messages[messages.length - 1].role === 'user' && (

Gemini

)}
{/* Input Area */}
setInput(e.target.value)} onKeyDown={handleKeyPress} onPaste={(e) => { // Allow paste - default behavior e.stopPropagation() }} placeholder="Ask Gemini..." className="flex-1 bg-gray-100 rounded-full px-4 py-2 text-sm focus:outline-none focus:ring-2 focus:ring-blue-200 transition-all select-text" disabled={isLoading} />
) }