<template>
  <div class="chat-view">
    <ChatSidebar
      v-if="showSidebar"
      :conversations="chatStore.conversations"
      :current-id="chatStore.currentConversationId"
      @create="chatStore.createConversation"
      @select="chatStore.selectConversation"
      @delete="chatStore.deleteConversation"
    />
    <div class="chat-view__main">
      <div v-if="!chatStore.currentConversationId" class="chat-view__empty">
        <a-empty description="选择一个对话或创建新对话开始聊天">
          <a-button type="primary" @click="chatStore.createConversation">
            <template #icon><PlusOutlined /></template>
            新建对话
          </a-button>
        </a-empty>
      </div>
      <template v-else>
        <StickyModeHeader />
        <PhaseIndicator />
        <div class="chat-view__content" ref="messagesContainer">
          <div class="chat-view__content-inner">
            <div v-if="chatStore.currentMessages.length === 0" class="chat-view__welcome">
              <div class="chat-view__welcome-inner">
                <div class="chat-view__welcome-logo">
                  <RobotOutlined class="chat-view__welcome-icon" />
                </div>
                <h2 class="chat-view__welcome-title">Fischer AgentKit</h2>
                <p class="chat-view__welcome-subtitle">企业级 AI 智能体平台</p>
                <div class="chat-view__welcome-hints">
                  <div class="chat-view__hint" v-for="hint in welcomeHints" :key="hint">
                    <ThunderboltOutlined class="chat-view__hint-icon" />
                    <span>{{ hint }}</span>
                  </div>
                </div>
              </div>
            </div>
            <ChatMessage
              v-for="msg in chatStore.currentMessages"
              :key="msg.id"
              :message="msg"
            />
            <!-- Streaming steps (structured) -->
            <div v-if="chatStore.streamingSteps.length > 0" class="chat-view__steps">
              <div class="chat-view__steps-header">
                <a-typography-text type="secondary">
                  <LoadingOutlined /> 执行中
                </a-typography-text>
                <span class="chat-view__steps-count">{{ chatStore.streamingSteps.length }} 步</span>
              </div>
              <ul class="chat-view__steps-list">
                <li
                  v-for="step in chatStore.streamingSteps"
                  :key="step.id"
                  class="chat-view__step"
                  :class="[
                    `chat-view__step--${step.type}`,
                    `chat-view__step--${step.status}`,
                  ]"
                >
                  <span class="chat-view__step-icon" :class="`chat-view__step-icon--${step.status}`">
                    <template v-if="step.status === 'running'"><LoadingOutlined /></template>
                    <template v-else-if="step.status === 'success'"><CheckOutlined /></template>
                    <template v-else><CloseOutlined /></template>
                  </span>
                  <span class="chat-view__step-label">{{ step.label }}</span>
                  <span v-if="step.detail" class="chat-view__step-detail">{{ step.detail }}</span>
                  <span v-if="step.type === 'streaming' && step.status === 'running' && step.counter !== undefined" class="chat-view__step-counter">
                    {{ step.counter }} 字符
                  </span>
                </li>
              </ul>
            </div>
          </div>
        </div>
        <div class="chat-view__input-wrap">
          <div class="chat-view__input-inner">
            <ChatInput
              :disabled="chatStore.isLoading"
              :is-generating="chatStore.isLoading"
              @send="handleSend"
              @stop="chatStore.stopGeneration"
            />
          </div>
        </div>
      </template>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, watch, nextTick, onMounted, onUnmounted, computed } from 'vue'
import { useRoute } from 'vue-router'
import { Empty as AEmpty, Button as AButton, Typography as ATypography } from 'ant-design-vue'
import {
  PlusOutlined,
  RobotOutlined,
  LoadingOutlined,
  CheckOutlined,
  CloseOutlined,
  ThunderboltOutlined,
} from '@ant-design/icons-vue'
import { useChatStore } from '@/stores/chatStore'
import ChatSidebar from '@/components/chat/ChatSidebar.vue'
import ChatMessage from '@/components/chat/ChatMessage.vue'
import ChatInput from '@/components/chat/ChatInput.vue'
import StickyModeHeader from '@/components/chat/StickyModeHeader.vue'
import PhaseIndicator from '@/components/chat/PhaseIndicator.vue'

const ATypographyText = ATypography.Text

const route = useRoute()
const chatStore = useChatStore()

const showSidebar = computed(() => {
  return !(route.name === 'agent-chat' || route.name === 'agent-preview')
})
const messagesContainer = ref<HTMLElement | null>(null)

const welcomeHints = [
  '智能路由 — 自动匹配最优技能',
  '工具调用 — 读写文件、执行命令',
  '流式响应 — 实时查看推理过程',
  '私董会 — 点击输入框旁「私董会」按钮召集专家团讨论',
]

onMounted(async () => {
  await chatStore.loadConversations()
  chatStore.connectWebSocket()
  // Auto-select or create a conversation so user can start chatting immediately
  if (chatStore.conversations.length > 0 && !chatStore.currentConversationId) {
    chatStore.selectConversation(chatStore.conversations[0].id)
  } else if (chatStore.conversations.length === 0) {
    chatStore.createConversation()
  }
})

onUnmounted(() => {
  chatStore.disconnectWebSocket()
})

// Auto-scroll to bottom when new messages arrive
watch(
  () => chatStore.currentMessages.length,
  async () => {
    await nextTick()
    scrollToBottom()
  }
)

watch(
  () => chatStore.streamingSteps.length,
  async () => {
    await nextTick()
    scrollToBottom()
  }
)

function scrollToBottom(): void {
  if (messagesContainer.value) {
    messagesContainer.value.scrollTop = messagesContainer.value.scrollHeight
  }
}

function handleSend(message: string, model?: string): void {
  if (chatStore.isWsConnected) {
    chatStore.sendWsMessage(message, undefined, model)
  } else {
    chatStore.sendMessage(message)
  }
}
</script>

<style scoped>
.chat-view {
  display: flex;
  /* 2026-07-01: 用 flex:1 + min-height:0 替代 height:100%。
   *
   * .chat-view 是 .agent-layout__chat-main (flex:1, flex-direction:column)
   * 的直接子元素。height:100% 在 flex-column 容器中引用父容器 height，
   * 但父容器自身依赖 flex:1 撑开（无显式 height），在某些 WebView 引擎
   * 中 height:100% 无法解析 → 窗口放大时聊天区域不跟随拉伸。
   * flex:1 + min-height:0 是 flexbox 标准写法，在所有引擎中一致工作。 */
  flex: 1;
  min-height: 0;
  overflow: hidden;
}

.chat-view__main {
  flex: 1;
  display: flex;
  flex-direction: column;
  overflow: hidden;
  background: var(--bg-primary);
}

.chat-view__empty {
  flex: 1;
  display: flex;
  align-items: center;
  justify-content: center;
}

.chat-view__content {
  flex: 1;
  overflow-y: auto;
  padding: var(--space-4);
}

.chat-view__content-inner {
  max-width: var(--max-chat-width);
  margin: 0 auto;
  width: 100%;
  min-height: 100%;
  display: flex;
  flex-direction: column;
}

.chat-view__welcome {
  display: flex;
  flex-direction: column;
  /* 2026-07-01: 外层块水平居中，但内部文字保持左对齐（见 .chat-view__welcome-inner 的 align-items: flex-start） */
  align-items: center;
  justify-content: flex-start;
  padding: 120px 0 48px;
  flex: 1;
  color: var(--text-placeholder);
}

.chat-view__welcome-inner {
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: var(--space-2);
  animation: welcomeFadeIn 0.4s ease-out;
}

@keyframes welcomeFadeIn {
  from { opacity: 0; transform: translateY(8px); }
  to { opacity: 1; transform: translateY(0); }
}

.chat-view__welcome-title {
  color: var(--text-primary);
  font-size: 24px;
  font-weight: var(--font-weight-semibold);
  margin: 0;
  letter-spacing: -0.02em;
}

.chat-view__welcome-subtitle {
  font-size: var(--font-base);
  color: var(--text-tertiary);
  margin: 0;
  line-height: 1.6;
}

.chat-view__welcome-hints {
  display: flex;
  flex-direction: column;
  gap: var(--space-1);
  margin-top: var(--space-5);
}

.chat-view__hint {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  font-size: var(--font-sm);
  color: var(--text-secondary);
  padding: 6px 0;
  line-height: 1.5;
}

.chat-view__hint-icon {
  font-size: 12px;
  color: var(--text-tertiary);
}

.chat-view__steps {
  padding: var(--space-3) var(--space-4);
  margin: var(--space-2) 0 0;
  background: var(--bg-primary);
  border-radius: var(--radius-lg);
  border: 1px solid var(--border-color);
  box-shadow: var(--shadow-sm);
  display: flex;
  flex-direction: column;
  gap: var(--space-2);
}

.chat-view__steps-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-2);
}

.chat-view__steps-count {
  font-size: var(--font-xs);
  color: var(--text-tertiary);
  background: var(--bg-secondary);
  padding: 1px var(--space-2);
  border-radius: var(--radius-sm);
}

.chat-view__steps-list {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: 4px;
  max-height: 240px;
  overflow-y: auto;
}

.chat-view__input-wrap {
  padding: var(--space-3) var(--space-4) var(--space-4);
  background: var(--bg-primary);
}

.chat-view__input-inner {
  max-width: var(--max-chat-width);
  margin: 0 auto;
  width: 100%;
}

.chat-view__step {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  padding: 4px 0;
  font-size: var(--font-sm);
  color: var(--text-secondary);
}

.chat-view__step-icon {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 16px;
  height: 16px;
  font-size: 12px;
  flex-shrink: 0;
}

.chat-view__step-icon--running {
  color: var(--color-primary);
  animation: chat-view__step-pulse 1.4s ease-in-out infinite;
}

.chat-view__step-icon--success {
  color: var(--color-success, #10b981);
}

.chat-view__step-icon--error {
  color: var(--color-error, #ef4444);
}

@keyframes chat-view__step-pulse {
  0%, 100% { opacity: 0.45; }
  50% { opacity: 1; }
}

.chat-view__step-label {
  font-weight: var(--font-weight-medium, 500);
  color: var(--text-primary);
}

.chat-view__step-detail {
  color: var(--text-tertiary);
  font-size: var(--font-xs);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  max-width: 320px;
}

.chat-view__step-counter {
  margin-left: auto;
  font-variant-numeric: tabular-nums;
  font-size: var(--font-xs);
  color: var(--text-tertiary);
  background: var(--bg-secondary);
  padding: 1px var(--space-2);
  border-radius: var(--radius-sm);
  white-space: nowrap;
}

.chat-view__step--error .chat-view__step-label,
.chat-view__step--error .chat-view__step-detail {
  color: var(--color-error, #ef4444);
}
</style>
