import { useEffect, useRef, useState, useCallback } from 'react'
import ReactMarkdown from 'react-markdown'
import remarkGfm from 'remark-gfm'
import {
  Hash,
  Crown,
  Send,
  AtSign,
  Copy,
  Check,
  FileText,
  ExternalLink,
} from 'lucide-react'
import { useStore } from '../store'
import type { Message } from '../types'

export function ChatView() {
  const { activeRoomId, rooms, messages, sendMessage, user } = useStore()
  const [input, setInput] = useState('')
  const [mentionQuery, setMentionQuery] = useState<string | null>(null)
  const [mentionIndex, setMentionIndex] = useState(0)
  const inputRef = useRef<HTMLTextAreaElement>(null)
  const bottomRef = useRef<HTMLDivElement>(null)

  const room = rooms.find(r => r.id === activeRoomId)
  const msgs: Message[] = activeRoomId ? (messages[activeRoomId] || []) : []
  const mode = room?.mode || 'plan'

  // Build agent list for @ mentions
  const mentionCandidates = room
    ? [room.master, ...(room.members || [])].filter(Boolean)
    : []

  const filteredMentions = mentionQuery !== null
    ? mentionCandidates.filter(name =>
        name.toLowerCase().includes(mentionQuery.toLowerCase())
      )
    : []

  // Detect @ trigger from input
  const updateMention = useCallback((value: string, cursorPos: number) => {
    const before = value.slice(0, cursorPos)
    const atMatch = before.match(/@(\w*)$/)
    if (atMatch) {
      setMentionQuery(atMatch[1])
      setMentionIndex(0)
    } else {
      setMentionQuery(null)
    }
  }, [])

  const insertMention = useCallback((name: string) => {
    const el = inputRef.current
    if (!el) return
    const cursorPos = el.selectionStart || input.length
    const before = input.slice(0, cursorPos)
    const after = input.slice(cursorPos)
    const atIdx = before.lastIndexOf('@')
    const newInput = before.slice(0, atIdx) + `@${name} ` + after
    setInput(newInput)
    setMentionQuery(null)
    setTimeout(() => {
      const pos = atIdx + name.length + 2
      el.setSelectionRange(pos, pos)
      el.focus()
    })
  }, [input])

  const toggleMode = useCallback(() => {
    if (!activeRoomId) return
    const newMode = mode === 'build' ? 'plan' : 'build'
    // 发送到后端
    const { ws } = useStore.getState()
    const socket = ws[activeRoomId]
    if (socket) {
      socket.send(JSON.stringify({ type: 'set_mode', mode: newMode }))
    }
    // 本地立即更新
    useStore.setState(s => ({
      rooms: s.rooms.map(r => r.id === activeRoomId ? { ...r, mode: newMode } : r)
    }))
  }, [activeRoomId, mode])

  useEffect(() => { bottomRef.current?.scrollIntoView({ behavior: 'smooth' }) }, [msgs, room?.status])

  if (!room) {
    return (
      <div className="flex-1 flex flex-col items-center justify-center bg-[var(--bg-primary)] text-[var(--text-muted)]">
        <Hash className="w-16 h-16 mb-4 opacity-20" />
        <p className="text-lg">选择一个项目开始聊天</p>
      </div>
    )
  }

  const statusLabel = room.status === 'working' && room.activeAgent
    ? `${room.activeAgent} ${room.action || ''}`
    : room.status === 'thinking' ? '思考中...' : room.status === 'working' ? '工作中...' : '空闲'

  return (
    <div className="flex flex-1 overflow-hidden bg-[var(--bg-primary)]">
      {/* Main chat area */}
      <div className="flex flex-col flex-1 min-w-0">
        {/* Header */}
        <div className="h-12 px-4 border-b border-[var(--border)] flex items-center gap-2 bg-[var(--bg-secondary)] shadow-sm">
          <Hash className="w-5 h-5 text-[var(--text-muted)]" />
          <span className="font-semibold text-base">{room.name}</span>
          <div className="h-6 w-[1px] bg-[var(--border)] mx-2" />
          <span className="text-sm text-[var(--text-muted)] truncate">
            {room.team || '项目群'}
          </span>
          <div className="flex-1" />
          {/* Status badge */}
          <span
            className={`text-xs px-2 py-1 rounded-full font-medium flex items-center gap-1.5 ${
              room.status === 'pending' ? 'bg-[var(--bg-tertiary)] text-[var(--text-muted)]' :
              room.status === 'thinking' ? 'bg-[var(--color-warning)]/20 text-[var(--color-warning)]' :
              'bg-[var(--color-success)]/20 text-[var(--color-success)]'
            }`}
          >
            <span className={`w-1.5 h-1.5 rounded-full ${
              room.status === 'pending' ? 'bg-[var(--text-muted)]' :
              room.status === 'thinking' ? 'bg-[var(--color-warning)] animate-pulse' :
              'bg-[var(--color-success)] animate-pulse'
            }`} />
            {statusLabel}
          </span>
        </div>

        {/* Messages */}
        <div className="flex-1 overflow-y-auto p-4 space-y-1 scrollbar-thin">
          {msgs.length === 0 && (
            <div className="flex flex-col items-center justify-center h-full text-[var(--text-muted)]">
              <Hash className="w-12 h-12 mb-2 opacity-30" />
              <p className="text-sm">这里是 {room.name} 的开始</p>
              <p className="text-xs mt-1">发送消息开始对话</p>
            </div>
          )}
          {msgs.map(msg =>
            msg.role === 'artifact' ? (
              <ArtifactCard key={msg.id} msg={msg} roomId={activeRoomId!} />
            ) : (
              <MessageBubble key={msg.id} msg={msg} userName={user?.name} />
            )
          )}
          {/* Thinking indicator */}
          {room.status === 'thinking' && msgs[msgs.length - 1]?.role === 'user' && (
            <ThinkingBubble agent={room.master} />
          )}
          <div ref={bottomRef} />
        </div>

        {/* Input area */}
        <div className="px-4 pb-4">
          <div className="relative">
            {/* @ Mention dropdown */}
            {mentionQuery !== null && filteredMentions.length > 0 && (
              <div className="absolute bottom-full left-0 right-0 mb-1 bg-[var(--bg-secondary)] border border-[var(--border)] rounded-lg shadow-lg overflow-hidden z-10">
                <div className="px-3 py-1.5 text-[10px] font-semibold text-[var(--text-muted)] uppercase">
                  成员
                </div>
                {filteredMentions.map((name, i) => {
                  const isMaster = name === room.master
                  return (
                    <button
                      key={name}
                      className={`w-full flex items-center gap-2 px-3 py-1.5 text-sm transition-colors ${
                        i === mentionIndex
                          ? 'bg-[var(--accent)] text-white'
                          : 'hover:bg-[var(--bg-hover)]'
                      }`}
                      onMouseEnter={() => setMentionIndex(i)}
                      onMouseDown={e => {
                        e.preventDefault()
                        insertMention(name)
                      }}
                    >
                      <div className={`w-6 h-6 rounded-full flex items-center justify-center text-white text-xs font-semibold flex-shrink-0 ${
                        isMaster ? 'bg-[var(--color-warning)]' : 'bg-[var(--accent)]'
                      }`}>
                        {isMaster ? <Crown className="w-3 h-3" /> : name[0]?.toUpperCase()}
                      </div>
                      <span className="truncate">{name}</span>
                      {isMaster && (
                        <span className={`text-[10px] px-1 py-0.5 rounded font-medium ml-auto ${
                          i === mentionIndex
                            ? 'bg-white/20 text-white'
                            : 'bg-[var(--color-warning)]/20 text-[var(--color-warning)]'
                        }`}>
                          MASTER
                        </span>
                      )}
                    </button>
                  )
                })}
              </div>
            )}

            {/* Input bar with mode toggle */}
            <div className="bg-[var(--bg-tertiary)] rounded-lg flex items-center gap-0 px-2 py-1.5">
              {/* Mode toggle - OpenCode style */}
              <button
                onClick={toggleMode}
                className={`
                  flex items-center gap-1 px-3 py-1.5 rounded-md text-xs font-bold tracking-wider transition-all duration-200 select-none flex-shrink-0
                  ${mode === 'build'
                    ? 'bg-orange-500 text-white shadow-sm shadow-orange-500/30'
                    : 'bg-blue-500/15 text-blue-400 hover:bg-blue-500/25'
                  }
                `}
                title="Tab 切换模式"
              >
                {mode === 'build' ? 'BUILD' : 'PLAN'}
              </button>
              <div className="h-5 w-[1px] bg-[var(--border)] mx-2 flex-shrink-0" />
              <textarea
                ref={inputRef}
                rows={1}
                className="flex-1 bg-transparent outline-none text-sm placeholder:text-[var(--text-muted)] min-w-0 resize-none max-h-[120px] leading-5 py-0.5"
                placeholder={mode === 'build' ? '发送确认开始执行任务...' : `#${room.name} 中发送消息...`}
                value={input}
                onChange={e => {
                  setInput(e.target.value)
                  // 自动调整高度
                  const el = e.target
                  el.style.height = 'auto'
                  el.style.height = Math.min(el.scrollHeight, 120) + 'px'
                  updateMention(e.target.value, e.target.selectionStart || 0)
                }}
                onKeyDown={e => {
                  // 输入法正在组合（选字）时，不拦截任何按键
                  if (e.nativeEvent.isComposing) return

                  // 提及下拉菜单键盘控制
                  if (mentionQuery !== null && filteredMentions.length > 0) {
                    if (e.key === 'ArrowUp') {
                      e.preventDefault()
                      setMentionIndex(i => (i - 1 + filteredMentions.length) % filteredMentions.length)
                      return
                    }
                    if (e.key === 'ArrowDown') {
                      e.preventDefault()
                      setMentionIndex(i => (i + 1) % filteredMentions.length)
                      return
                    }
                    if (e.key === 'Enter' || e.key === 'Tab') {
                      e.preventDefault()
                      insertMention(filteredMentions[mentionIndex])
                      return
                    }
                    if (e.key === 'Escape') {
                      e.preventDefault()
                      setMentionQuery(null)
                      return
                    }
                  }
                  // Tab 切换模式（无提及下拉时）
                  if (e.key === 'Tab') {
                    e.preventDefault()
                    toggleMode()
                    return
                  }
                  // Shift+Enter 换行（默认行为，不拦截）
                  // Enter 发送消息
                  if (e.key === 'Enter' && !e.shiftKey) {
                    e.preventDefault()
                    if (input.trim()) {
                      sendMessage(room.id, input.trim())
                      setInput('')
                      setMentionQuery(null)
                      // 重置高度
                      const el = inputRef.current
                      if (el) el.style.height = 'auto'
                    }
                  }
                }}
              />
              <button
                className="text-[var(--text-muted)] hover:text-[var(--text-primary)] transition-colors p-1.5"
                title="@ 提及"
                onClick={() => {
                  setInput(prev => prev + '@')
                  setMentionQuery('')
                  setMentionIndex(0)
                  inputRef.current?.focus()
                }}
              >
                <AtSign className="w-5 h-5" />
              </button>
              <button
                className="text-[var(--accent)] hover:text-[var(--accent-hover)] transition-colors disabled:opacity-50 p-1.5"
                disabled={!input.trim()}
                onClick={() => {
                  if (input.trim()) {
                    sendMessage(room.id, input.trim())
                    setInput('')
                    setMentionQuery(null)
                  }
                }}
              >
                <Send className="w-5 h-5" />
              </button>
            </div>
            {/* Tab hint */}
            <div className="flex items-center gap-2 mt-1 px-1">
              <span className="text-[10px] text-[var(--text-muted)] opacity-60">
                <kbd className="px-1 py-0.5 bg-[var(--bg-tertiary)] rounded text-[9px] border border-[var(--border)]">Tab</kbd> 切换模式
              </span>
            </div>
          </div>
        </div>
      </div>
    </div>
  )
}

function highlightMentions(content: string): string {
  if (!content) return ''
  return content.replace(/@(\w+)/g, '**@$1**')
}

/* ---- Artifact Card ---- */
function ArtifactCard({ msg, roomId }: { msg: Message; roomId: string }) {
  const [copied, setCopied] = useState(false)

  const avatarColors = [
    'bg-red-500', 'bg-orange-500', 'bg-amber-500', 'bg-yellow-500',
    'bg-lime-500', 'bg-green-500', 'bg-emerald-500', 'bg-teal-500',
    'bg-cyan-500', 'bg-sky-500', 'bg-blue-500', 'bg-indigo-500',
    'bg-violet-500', 'bg-purple-500', 'bg-fuchsia-500', 'bg-pink-500', 'bg-rose-500'
  ]
  const agentName = msg.agent || 'Unknown'
  const colorIndex = agentName.charCodeAt(0) % avatarColors.length

  const openArtifact = () => {
    if (!msg.filename) return
    const event = new CustomEvent('open-artifact', { detail: { roomId, filename: msg.filename } })
    window.dispatchEvent(event)
  }

  const copyFilename = () => {
    navigator.clipboard.writeText(msg.filename || '')
    setCopied(true)
    setTimeout(() => setCopied(false), 2000)
  }

  return (
    <div className="flex gap-3">
      <div className={`w-10 h-10 rounded-full flex items-center justify-center text-white font-semibold flex-shrink-0 mt-0.5 ${avatarColors[colorIndex]}`}>
        {agentName[0]?.toUpperCase()}
      </div>
      <div className="flex flex-col items-start max-w-[70%]">
        <div className="flex items-center gap-2 mb-0.5">
          <span className="font-medium text-sm text-[var(--text-primary)]">{agentName}</span>
          <span className="text-[10px] px-1.5 py-0.5 bg-emerald-500/20 text-emerald-400 rounded font-medium">
            已完成
          </span>
        </div>
        <button
          onClick={openArtifact}
          className="w-full bg-[var(--bg-tertiary)] border border-[var(--border)] rounded-lg p-3 hover:border-[var(--accent)] transition-colors text-left group"
        >
          <div className="flex items-start gap-3">
            <div className="w-10 h-10 rounded-lg bg-[var(--accent)]/10 flex items-center justify-center flex-shrink-0">
              <FileText className="w-5 h-5 text-[var(--accent)]" />
            </div>
            <div className="flex-1 min-w-0">
              <div className="font-medium text-sm text-[var(--text-primary)] truncate">
                {msg.title || msg.filename}
              </div>
              <div className="text-xs text-[var(--text-muted)] mt-0.5">{msg.filename}</div>
            </div>
            <ExternalLink className="w-4 h-4 text-[var(--text-muted)] opacity-0 group-hover:opacity-100 transition-opacity flex-shrink-0 mt-1" />
          </div>
        </button>
        <div className="flex items-center gap-1 mt-0.5">
          <button
            onClick={openArtifact}
            className="flex items-center gap-1 px-1.5 py-0.5 rounded text-[10px] text-[var(--text-muted)] hover:text-[var(--accent)] hover:bg-[var(--bg-hover)] transition-colors"
          >
            <FileText className="w-3 h-3" />
            查看文档
          </button>
          <button
            onClick={copyFilename}
            className="flex items-center gap-1 px-1.5 py-0.5 rounded text-[10px] text-[var(--text-muted)] hover:text-[var(--text-primary)] hover:bg-[var(--bg-hover)] transition-colors"
          >
            {copied ? <Check className="w-3 h-3" /> : <Copy className="w-3 h-3" />}
            {copied ? '已复制' : '复制'}
          </button>
        </div>
      </div>
    </div>
  )
}

/* ---- Message Bubble ---- */
function MessageBubble({ msg, userName }: { msg: Message; userName?: string }) {
  const isUser = msg.role === 'user'
  const isMaster = msg.role === 'master'
  const agentName = msg.agent || 'Unknown'
  const [copied, setCopied] = useState(false)

  const avatarColors = [
    'bg-red-500', 'bg-orange-500', 'bg-amber-500', 'bg-yellow-500',
    'bg-lime-500', 'bg-green-500', 'bg-emerald-500', 'bg-teal-500',
    'bg-cyan-500', 'bg-sky-500', 'bg-blue-500', 'bg-indigo-500',
    'bg-violet-500', 'bg-purple-500', 'bg-fuchsia-500', 'bg-pink-500', 'bg-rose-500'
  ]
  const colorIndex = agentName.charCodeAt(0) % avatarColors.length
  const displayName = isUser ? (userName || agentName) : agentName

  const copyText = (text: string) => {
    navigator.clipboard.writeText(text)
    setCopied(true)
    setTimeout(() => setCopied(false), 2000)
  }

  return (
    <div className={`flex gap-3 group ${isUser ? 'flex-row-reverse' : ''}`}>
      <div className={`w-10 h-10 rounded-full flex items-center justify-center text-white font-semibold flex-shrink-0 mt-0.5 ${isUser ? 'bg-[var(--accent)]' : avatarColors[colorIndex]}`}>
        {isMaster ? <Crown className="w-5 h-5" /> : displayName[0]?.toUpperCase()}
      </div>
      <div className={`flex flex-col max-w-[70%] ${isUser ? 'items-end' : 'items-start'}`}>
        <div className={`flex items-center gap-2 mb-0.5 ${isUser ? 'flex-row-reverse' : ''}`}>
          <span className={`font-medium text-sm ${isMaster ? 'text-[var(--color-warning)]' : isUser ? 'text-[var(--accent)]' : 'text-[var(--text-primary)]'}`}>
            {displayName}
          </span>
          {isMaster && (
            <span className="text-[10px] px-1 py-0.5 bg-[var(--color-warning)]/20 text-[var(--color-warning)] rounded font-medium">
              MASTER
            </span>
          )}
        </div>
        <div
          className={`
            px-3.5 py-2 rounded-lg text-sm relative
            ${isUser
              ? 'bg-[var(--accent)] text-white rounded-tr-sm'
              : isMaster
              ? 'bg-[var(--bg-tertiary)] border-l-4 border-[var(--color-warning)] rounded-tl-sm'
              : 'bg-[var(--bg-tertiary)] rounded-tl-sm'
            }
          `}
        >
          <div className="prose prose-sm dark:prose-invert max-w-none">
            <ReactMarkdown remarkPlugins={[remarkGfm]}>
              {highlightMentions(msg.content)}
            </ReactMarkdown>
          </div>
          {msg.streaming && (
            <span className="inline-block w-1.5 h-3 bg-[var(--text-muted)] animate-pulse ml-0.5" />
          )}
        </div>
        {!isUser && !msg.streaming && msg.content && (
          <div className="flex items-center gap-1 mt-0.5 opacity-0 group-hover:opacity-100 transition-opacity">
            <button
              onClick={() => copyText(msg.content)}
              className="flex items-center gap-1 px-1.5 py-0.5 rounded text-[10px] text-[var(--text-muted)] hover:text-[var(--text-primary)] hover:bg-[var(--bg-hover)] transition-colors"
              title="复制消息"
            >
              {copied ? <Check className="w-3 h-3" /> : <Copy className="w-3 h-3" />}
              {copied ? '已复制' : '复制'}
            </button>
          </div>
        )}
      </div>
    </div>
  )
}

function ThinkingBubble({ agent }: { agent: string }) {
  return (
    <div className="flex gap-3">
      <div className="w-10 h-10 rounded-full bg-[var(--color-warning)]/20 flex items-center justify-center flex-shrink-0 mt-0.5">
        <Crown className="w-5 h-5 text-[var(--color-warning)]" />
      </div>
      <div className="flex flex-col items-start">
        <span className="font-medium text-sm text-[var(--color-warning)] mb-0.5">{agent || 'Master'}</span>
        <div className="px-3.5 py-2.5 rounded-lg bg-[var(--bg-tertiary)] border-l-4 border-[var(--color-warning)] rounded-tl-sm flex items-center gap-1.5">
          <span className="w-2 h-2 rounded-full bg-[var(--color-warning)] animate-bounce" style={{ animationDelay: '0ms' }} />
          <span className="w-2 h-2 rounded-full bg-[var(--color-warning)] animate-bounce" style={{ animationDelay: '150ms' }} />
          <span className="w-2 h-2 rounded-full bg-[var(--color-warning)] animate-bounce" style={{ animationDelay: '300ms' }} />
        </div>
      </div>
    </div>
  )
}
