<template>
  <div class="algorithm-showcase-container">
    <!-- 左侧算法服务一览 -->
    <div class="left-sidebar">
      <div class="sidebar-header">
        <h2>AI算法</h2>
        <p>{{ algorithmStore.algorithms.length }}个算法</p>
      </div>
      
      <div class="algorithm-categories">
        <div 
          v-for="(category, key) in categories" 
          :key="key"
          class="category-item"
        >
          <div class="category-header">
            <div class="category-icon" :style="{ backgroundColor: category.color }">
              <component :is="category.icon" />
            </div>
            <h3>{{ category.name }}</h3>
            <span class="algorithm-count">{{ getAlgorithmsByCategory(key).length }}个算法</span>
          </div>
          
          <div class="algorithm-list">
            <div 
              v-for="algorithm in getAlgorithmsByCategory(key)" 
              :key="algorithm.id"
              class="algorithm-item"
              :class="{ active: selectedAlgorithm && selectedAlgorithm.id === algorithm.id }"
              @click="selectAlgorithm(algorithm)"
            >
              <span class="algorithm-name">{{ algorithm.name }}</span>
              <el-tag size="small" type="info">{{ getOutputTypeName(algorithm.output_type) }}</el-tag>
            </div>
          </div>
        </div>
      </div>
    </div>
    
    <!-- 中间内容区域 -->
    <div class="main-content">
      <!-- 视频/图片展示 -->
      <div class="media-display">
        <div v-if="!uploadedFile" class="media-placeholder">
          <el-icon class="play-icon"><VideoPlay /></el-icon>
          <p>请上传或选择演示素材</p>
          <p class="support-text">支持视频和图片格式</p>
        </div>
        
        <div v-else-if="isImageFile" class="image-preview">
          <img :src="uploadedFile.url" alt="上传图片" />
        </div>
        
        <div v-else-if="isVideoFile" class="video-preview">
          <video controls :src="uploadedFile.url">
            您的浏览器不支持视频播放
          </video>
        </div>
      </div>
      
      <!-- 素材上传 -->
      <div class="upload-section">
        <div class="section-header">
          <h3>素材上传</h3>
          <el-tag v-if="!userStore.isLoggedIn" type="warning" size="small">
            <el-icon><Warning /></el-icon>
            需要登录
          </el-tag>
        </div>
        <div class="upload-tabs">
          <el-tabs v-model="activeUploadTab">
            <el-tab-pane label="视频数据" name="video">
              <div class="upload-area">
                <el-upload
                  class="upload-demo"
                  drag
                  action="#"
                  :auto-upload="false"
                  :on-change="handleFileChange"
                  :accept="'.mp4,.avi,.mov,.wmv'"
                >
                  <el-icon class="el-icon--upload"><Upload /></el-icon>
                  <div class="el-upload__text">点击或拖拽文件到此处上传</div>
                  <template #tip>
                    <div class="el-upload__tip">
                      支持 MP4、AVI、MOV 格式
                    </div>
                  </template>
                </el-upload>
                
                <div class="demo-videos">
                  <h4>演示视频：</h4>
                  <div class="demo-video-list">
                    <div 
                      v-for="(demo, index) in demoVideos" 
                      :key="index"
                      class="demo-video-item"
                      @click="selectDemoVideo(demo)"
                    >
                      <div class="demo-video-thumbnail">
                        <el-icon class="play-icon"><VideoPlay /></el-icon>
                      </div>
                      <span>{{ demo.name }}</span>
                    </div>
                  </div>
                </div>
              </div>
            </el-tab-pane>
            
            <el-tab-pane label="图片/图表" name="image">
              <div class="upload-area">
                <el-upload
                  class="upload-demo"
                  drag
                  action="#"
                  :auto-upload="false"
                  :on-change="handleFileChange"
                  :accept="'.jpg,.jpeg,.png,.gif'"
                >
                  <el-icon class="el-icon--upload"><Upload /></el-icon>
                  <div class="el-upload__text">点击或拖拽文件到此处上传</div>
                  <template #tip>
                    <div class="el-upload__tip">
                      支持 JPG、PNG、GIF 格式
                    </div>
                  </template>
                </el-upload>
                
                <div class="demo-images">
                  <h4>演示图片：</h4>
                  <div class="demo-image-list">
                    <div 
                      v-for="(demo, index) in demoImages" 
                      :key="index"
                      class="demo-image-item"
                      @click="selectDemoImage(demo)"
                    >
                      <img :src="demo.url" :alt="demo.name" />
                      <span>{{ demo.name }}</span>
                    </div>
                  </div>
                </div>
              </div>
            </el-tab-pane>
            
            <el-tab-pane label="标注工具" name="annotation">
              <div class="annotation-tools">
                <p>标注工具功能开发中...</p>
              </div>
            </el-tab-pane>
          </el-tabs>
        </div>
      </div>
      
      <!-- 算法执行 -->
      <div class="algorithm-execution">
        <div class="section-header">
          <h3>算法执行</h3>
          <el-tag v-if="!userStore.isLoggedIn" type="warning" size="small">
            <el-icon><Warning /></el-icon>
            需要登录
          </el-tag>
        </div>
        <div class="execution-form">
          <el-form :inline="true" class="execution-form">
            <el-form-item label="选择算法模型">
              <el-select 
                v-model="selectedModel" 
                placeholder="请选择算法..."
                style="width: 200px"
              >
                <el-option 
                  v-for="algorithm in algorithmStore.algorithms" 
                  :key="algorithm.id"
                  :label="algorithm.name"
                  :value="algorithm.id"
                />
              </el-select>
            </el-form-item>
            
            <el-form-item>
              <el-button 
                type="primary" 
                @click="executeAlgorithm"
                :loading="executing"
                :disabled="!selectedAlgorithm || !uploadedFile"
              >
                <el-icon><VideoPlay /></el-icon>
                运行算法
              </el-button>
            </el-form-item>
          </el-form>
          
          <div v-if="executionProgress > 0" class="execution-progress">
            <el-progress 
              :percentage="executionProgress" 
              :status="executionStatus"
            />
            <p class="progress-text">{{ executionMessage }}</p>
          </div>
        </div>
      </div>
    </div>
    
    <!-- 右侧运行结果 -->
    <div class="right-sidebar">
      <div class="sidebar-header">
        <h2>运行结果</h2>
      </div>
      
      <div v-if="!executionResult" class="result-placeholder">
        <el-icon class="chart-icon"><DataAnalysis /></el-icon>
        <p>等待算法执行</p>
        <p class="placeholder-text">执行完成后将在此展示</p>
      </div>
      
      <div v-else class="result-content">
        <div class="result-header">
          <h3>{{ selectedAlgorithm && selectedAlgorithm.name || '算法' }} 执行结果</h3>
          <span class="execution-time">
            执行时间: {{ executionResult.response_time }}ms
          </span>
        </div>
        
        <div class="result-details">
          <el-descriptions :column="1" border>
            <el-descriptions-item label="执行状态">
              <el-tag :type="executionResult.status === 'success' ? 'success' : 'danger'">
                {{ executionResult.status === 'success' ? '成功' : '失败' }}
              </el-tag>
            </el-descriptions-item>
            <el-descriptions-item label="输出类型">
              {{ getOutputTypeName(selectedAlgorithm && selectedAlgorithm.output_type || '') }}
            </el-descriptions-item>
          </el-descriptions>
        </div>
        
        <div class="result-display">
          <h4>输出结果</h4>
          
          <div v-if="isImageResult" class="result-image">
            <img :src="executionResult.output_data.result?.image || executionResult.output_data.image" alt="结果图片" />
          </div>
          
          <div v-else-if="isVideoResult" class="result-video">
            <video 
              controls 
              autoplay 
              loop 
              :src="getVideoResultUrl()"
              @error="handleVideoError"
            >
              您的浏览器不支持视频播放
            </video>
          </div>
          
          <div v-else-if="isTextResult" class="result-text">
            <pre>{{ executionResult.output_data.text }}</pre>
          </div>
          
          <div v-else class="result-json">
            <pre>{{ JSON.stringify(executionResult.output_data, null, 2) }}</pre>
          </div>
        </div>
      </div>
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, computed, onMounted, onUnmounted } from 'vue'
import { useRouter } from 'vue-router'
import { ElMessage } from 'element-plus'
import axios from 'axios'
import { useAlgorithmStore } from '../stores/algorithm'
import { useUserStore } from '../stores/user'
import { 
  VideoPlay, 
  Upload, 
  DataAnalysis, 
  Grid, 
  MagicStick, 
  ArrowUp, 
  Camera, 
  Star,
  Warning 
} from '@element-plus/icons-vue'

// 获取路由和存储
const router = useRouter()
const algorithmStore = useAlgorithmStore()
const userStore = useUserStore()

// 响应式数据
const selectedAlgorithm = ref<any>(null)
const uploadedFile = ref<any>(null)
const selectedModel = ref('')
const executing = ref(false)
const executionProgress = ref(0)
const executionStatus = ref('')
const executionMessage = ref('')
const executionResult = ref<any>(null)
const activeUploadTab = ref('video')

// WebSocket 连接
let wsConnection: WebSocket | null = null
const realtimeDetections = ref<any[]>([])
const isRealtimeMode = ref(false)

// 连接到 WebSocket 服务器
const connectWebSocket = () => {
  const wsUrl = `ws://localhost:8766`
  
  try {
    wsConnection = new WebSocket(wsUrl)
    
    wsConnection.onopen = () => {
      console.log('[WS] Connected to WebSocket server')
      isRealtimeMode.value = true
    }
    
    wsConnection.onmessage = (event) => {
      try {
        const data = JSON.parse(event.data)
        console.log('[WS] Received:', data)
        
        if (data.msg_type === 'frame') {
          realtimeDetections.value.push(data)
          // 保持最近100帧
          if (realtimeDetections.value.length > 100) {
            realtimeDetections.value.shift()
          }
        } else if (data.msg_type === 'alert') {
          ElMessage.warning(`检测到异常: ${data.event_type}`)
        }
      } catch (e) {
        console.error('[WS] Parse error:', e)
      }
    }
    
    wsConnection.onerror = (error) => {
      console.error('[WS] Error:', error)
    }
    
    wsConnection.onclose = () => {
      console.log('[WS] Disconnected')
      isRealtimeMode.value = false
    }
  } catch (e) {
    console.error('[WS] Connection failed:', e)
  }
}

// 断开 WebSocket 连接
const disconnectWebSocket = () => {
  if (wsConnection) {
    wsConnection.close()
    wsConnection = null
  }
  isRealtimeMode.value = false
  realtimeDetections.value = []
}

// 分类配置
const categories = {
  computer_vision: {
    name: '计算机视觉',
    icon: Camera,
    color: '#409EFF'
  },
  video_processing: {
    name: '视频处理',
    icon: VideoPlay,
    color: '#67C23A'
  },
  nlp: {
    name: '自然语言处理',
    icon: Star,
    color: '#E6A23C'
  },
  ml: {
    name: '机器学习',
    icon: MagicStick,
    color: '#909399'
  },
  edge_computing: {
    name: '边缘计算',
    icon: Grid,
    color: '#F56C6C'
  },
  medical: {
    name: '医疗算法',
    icon: DataAnalysis,
    color: '#722ED1'
  },
  autonomous_driving: {
    name: '自动驾驶算法',
    icon: ArrowUp,
    color: '#FAAD14'
  }
}

// 演示视频
const demoVideos = [
  { id: 1, name: '街道交通监控', url: '' },
  { id: 2, name: '人群行为分析', url: '' }
]

// 演示图片
const demoImages = [
  { id: 1, name: '城市街景', url: '' },
  { id: 2, name: '人物肖像', url: '' }
]

// 输出类型映射
const outputTypes = {
  image: '图片',
  video: '视频',
  text: '文本',
  json: 'JSON',
  audio: '音频'
}

// 计算属性
const getOutputTypeName = (type: string) => {
  return outputTypes[type as keyof typeof outputTypes] || type
}

const getAlgorithmsByCategory = (category: string) => {
  return algorithmStore.algorithms.filter(algorithm => algorithm.tech_category === category)
}

const isImageFile = computed(() => {
  if (!uploadedFile.value) return false
  return uploadedFile.value.type.startsWith('image/')
})

const isVideoFile = computed(() => {
  if (!uploadedFile.value) return false
  return uploadedFile.value.type.startsWith('video/')
})

const isImageResult = computed(() => {
  if (!executionResult.value || !selectedAlgorithm.value) return false
  const outputData = executionResult.value.output_data || {}
  const result = outputData.result || outputData
  
  // 检查是否有图片数据
  if (result.image || result.image_url || result.output_image) return true
  return false
})

const isVideoResult = computed(() => {
  if (!executionResult.value || !selectedAlgorithm.value) return false
  const outputData = executionResult.value.output_data || {}
  const result = outputData.result || outputData
  
  // 检查是否有视频数据
  if (result.video || result.video_url || result.output_video) return true
  return false
})

const isTextResult = computed(() => {
  if (!executionResult.value || !selectedAlgorithm.value) return false
  return selectedAlgorithm.value.output_type === 'text'
})

const getVideoResultUrl = () => {
  if (!executionResult.value || !executionResult.value.output_data) return ''
  
  const outputData = executionResult.value.output_data || {}
  const result = outputData.result || outputData
  
  // 检查是否是base64编码的视频数据
  if (result.video && typeof result.video === 'string' && result.video.startsWith('data:')) {
    return result.video
  }
  
  // 检查是否有video_url
  if (result.video_url) {
    console.log('[DEBUG] video_url 原始值:', result.video_url)
    const url = result.video_url
    console.log('[DEBUG] video_url 返回值:', url)
    return url
  }
  
  // 检查是否有output_video
  if (result.output_video) {
    return result.output_video
  }
  
  return ''
}

const handleVideoError = (event: Event) => {
  console.error('视频加载失败:', event)
  ElMessage.error('视频加载失败，请检查算法输出格式')
}

// 方法
const selectAlgorithm = (algorithm: any) => {
  selectedAlgorithm.value = algorithm
  selectedModel.value = algorithm.id
}

const handleFileChange = async (file: any) => {
  // 检查用户是否登录
  if (!userStore.isLoggedIn) {
    ElMessage.warning('请先登录后再上传文件')
    router.push('/login')
    return
  }
  
  // 检查是否选择了算法
  if (!selectedAlgorithm.value) {
    ElMessage.warning('请先选择一个算法')
    return
  }
  
  try {
    // 创建临时URL用于预览
    const url = URL.createObjectURL(file.raw)
    
    // 上传文件到MinIO
    const formData = new FormData()
    formData.append('file', file.raw)
    formData.append('algorithm_id', selectedAlgorithm.value.id)
    
    // 调用后端API上传文件
    const response = await axios.post('/api/v1/data/media/upload', formData, {
      headers: { 'Content-Type': 'multipart/form-data' }
    })
    
    uploadedFile.value = {
      name: file.name,
      type: file.raw.type,
      url: url,
      file: file.raw,
      uploaded: true,
      filePath: response.data.file_path
    }
    
    ElMessage.success('文件上传成功')
  } catch (error: any) {
    console.error('文件上传失败:', error)
    ElMessage.error(error.response?.data?.detail || '文件上传失败')
    
    // 即使上传失败，也使用临时URL
    const url = URL.createObjectURL(file.raw)
    uploadedFile.value = {
      name: file.name,
      type: file.raw.type,
      url: url,
      file: file.raw,
      uploaded: false
    }
  }
}

const selectDemoVideo = (demo: any) => {
  // 这里可以设置演示视频的URL
  uploadedFile.value = {
    name: demo.name,
    type: 'video/mp4',
    url: demo.url || '',
    demo: true
  }
}

const selectDemoImage = (demo: any) => {
  // 这里可以设置演示图片的URL
  uploadedFile.value = {
    name: demo.name,
    type: 'image/jpeg',
    url: demo.url || '',
    demo: true
  }
}

const executeAlgorithm = async () => {
  if (!selectedAlgorithm.value || !uploadedFile.value) {
    ElMessage.warning('请先选择算法和上传文件')
    return
  }
  
  executing.value = true
  executionProgress.value = 0
  executionStatus.value = 'success'
  executionMessage.value = '正在执行算法...'
  
  try {
    // 获取算法的默认版本
    const defaultVersion = selectedAlgorithm.value.versions?.find((v: any) => v.is_default)
    if (!defaultVersion) {
      ElMessage.error('该算法没有可用的版本')
      executing.value = false
      return
    }
    
    // 准备调用参数 - 使用文件路径或MinIO路径
    const callRequest = {
      algorithm_id: selectedAlgorithm.value.id,
      version_id: defaultVersion.id,
      input_data: {
        video: uploadedFile.value.filePath || uploadedFile.value.url
      },
      params: {
        ws_url: 'ws://localhost:8766'
      }
    }
    
    // 调用算法API
    executionProgress.value = 30
    executionMessage.value = '正在调用算法...'
    console.log('Calling algorithm API with:', callRequest)
    
    const response = await axios.post('/api/v1/algorithms/call/public', callRequest)
    console.log('Algorithm response:', response.data)
    
    executionProgress.value = 80
    executionMessage.value = '正在处理结果...'
    
    // 设置执行结果
    executionResult.value = {
      id: response.data.id,
      status: response.data.status,
      output_data: response.data.output_data,
      response_time: response.data.response_time,
      error_message: response.data.error_message
    }
    
    executionProgress.value = 100
    executionMessage.value = '算法执行完成！'
    
    ElMessage.success('算法执行成功')
  } catch (error: any) {
    console.error('算法执行失败:', error)
    executionStatus.value = 'exception'
    executionMessage.value = '算法执行失败'
    
    executionResult.value = {
      id: 'error-' + Date.now(),
      status: 'error',
      output_data: {},
      response_time: 0,
      error_message: error.response?.data?.detail || '执行失败'
    }
    
    ElMessage.error(error.response?.data?.detail || '算法执行失败')
  } finally {
    executing.value = false
  }
}

// 初始化
onMounted(async () => {
  await algorithmStore.fetchAlgorithms()
  
  // 默认选择第一个算法
  if (algorithmStore.algorithms.length > 0) {
    selectAlgorithm(algorithmStore.algorithms[0])
  }
  
  // 连接 WebSocket 服务器
  connectWebSocket()
})

// 组件卸载时断开 WebSocket
onUnmounted(() => {
  disconnectWebSocket()
})
</script>

<style scoped>
.algorithm-showcase-container {
  display: flex;
  height: 100vh;
  background-color: #f5f7fa;
}

/* 左侧算法服务一览 */
.left-sidebar {
  width: 300px;
  background-color: #fff;
  border-right: 1px solid #e4e7ed;
  overflow-y: auto;
}

.sidebar-header {
  padding: 20px;
  border-bottom: 1px solid #e4e7ed;
}

.sidebar-header h2 {
  font-size: 18px;
  margin: 0 0 5px 0;
  color: #303133;
}

.sidebar-header p {
  font-size: 14px;
  color: #909399;
  margin: 0;
}

.algorithm-categories {
  padding: 10px 0;
}

.category-item {
  margin-bottom: 20px;
}

.category-header {
  display: flex;
  align-items: center;
  padding: 0 20px 10px;
  cursor: pointer;
}

.category-icon {
  width: 32px;
  height: 32px;
  border-radius: 4px;
  display: flex;
  align-items: center;
  justify-content: center;
  margin-right: 10px;
  color: #fff;
}

.category-header h3 {
  font-size: 14px;
  margin: 0;
  flex: 1;
  color: #303133;
}

.algorithm-count {
  font-size: 12px;
  color: #909399;
}

.algorithm-list {
  padding: 0 10px;
}

.algorithm-item {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 10px 15px;
  margin-bottom: 5px;
  border-radius: 4px;
  cursor: pointer;
  transition: all 0.3s;
}

.algorithm-item:hover {
  background-color: #f5f7fa;
}

.algorithm-item.active {
  background-color: #ecf5ff;
  border-left: 3px solid #409EFF;
}

.algorithm-name {
  font-size: 14px;
  color: #303133;
  flex: 1;
}

/* 中间内容区域 */
.main-content {
  flex: 1;
  display: flex;
  flex-direction: column;
  overflow-y: auto;
  padding: 20px;
}

/* 视频/图片展示 */
.media-display {
  flex: 1;
  background-color: #1f2937;
  border-radius: 8px;
  margin-bottom: 20px;
  min-height: 400px;
  display: flex;
  align-items: center;
  justify-content: center;
  position: relative;
  overflow: hidden;
}

.media-placeholder {
  text-align: center;
  color: #9ca3af;
}

.play-icon {
  font-size: 64px;
  margin-bottom: 20px;
  color: #4b5563;
}

.media-placeholder p {
  margin: 5px 0;
  font-size: 16px;
}

.support-text {
  font-size: 14px;
  color: #6b7280;
}

.image-preview {
  width: 100%;
  height: 100%;
  display: flex;
  align-items: center;
  justify-content: center;
}

.image-preview img {
  max-width: 100%;
  max-height: 100%;
  object-fit: contain;
}

.video-preview {
  width: 100%;
  height: 100%;
  display: flex;
  align-items: center;
  justify-content: center;
}

.video-preview video {
  max-width: 100%;
  max-height: 100%;
}

/* 素材上传 */
.upload-section {
  background-color: #fff;
  border-radius: 8px;
  padding: 20px;
  margin-bottom: 20px;
  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}

.section-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 15px;
}

.section-header h3 {
  font-size: 16px;
  margin: 0;
  color: #303133;
}

.upload-area {
  margin-top: 15px;
}

.demo-videos {
  margin-top: 20px;
}

.demo-videos h4 {
  font-size: 14px;
  margin: 0 0 10px 0;
  color: #606266;
}

.demo-video-list {
  display: flex;
  gap: 15px;
}

.demo-video-item {
  flex: 1;
  text-align: center;
  cursor: pointer;
  padding: 10px;
  border-radius: 4px;
  transition: all 0.3s;
}

.demo-video-item:hover {
  background-color: #f5f7fa;
}

.demo-video-thumbnail {
  width: 100%;
  height: 100px;
  background-color: #f5f7fa;
  border-radius: 4px;
  display: flex;
  align-items: center;
  justify-content: center;
  margin-bottom: 8px;
}

.demo-video-thumbnail .play-icon {
  font-size: 24px;
  color: #909399;
}

.demo-images {
  margin-top: 20px;
}

.demo-images h4 {
  font-size: 14px;
  margin: 0 0 10px 0;
  color: #606266;
}

.demo-image-list {
  display: flex;
  gap: 15px;
}

.demo-image-item {
  flex: 1;
  text-align: center;
  cursor: pointer;
  padding: 10px;
  border-radius: 4px;
  transition: all 0.3s;
}

.demo-image-item:hover {
  background-color: #f5f7fa;
}

.demo-image-item img {
  width: 100%;
  height: 100px;
  object-fit: cover;
  border-radius: 4px;
  margin-bottom: 8px;
}

/* 算法执行 */
.algorithm-execution {
  background-color: #fff;
  border-radius: 8px;
  padding: 20px;
  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}

.execution-form {
  margin-bottom: 15px;
}

.execution-progress {
  margin-top: 15px;
}

.progress-text {
  font-size: 14px;
  color: #606266;
  margin-top: 5px;
  text-align: center;
}

/* 右侧运行结果 */
.right-sidebar {
  width: 400px;
  background-color: #fff;
  border-left: 1px solid #e4e7ed;
  overflow-y: auto;
}

.right-sidebar .sidebar-header {
  padding: 20px;
  border-bottom: 1px solid #e4e7ed;
}

.right-sidebar .sidebar-header h2 {
  font-size: 18px;
  margin: 0;
  color: #303133;
}

.result-placeholder {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  height: 400px;
  text-align: center;
  color: #909399;
}

.chart-icon {
  font-size: 64px;
  margin-bottom: 20px;
  color: #dcdfe6;
}

.result-placeholder p {
  margin: 5px 0;
  font-size: 16px;
}

.placeholder-text {
  font-size: 14px;
  color: #c0c4cc;
}

.result-content {
  padding: 20px;
}

.result-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 20px;
}

.result-header h3 {
  font-size: 16px;
  margin: 0;
  color: #303133;
}

.execution-time {
  font-size: 12px;
  color: #909399;
}

.result-details {
  margin-bottom: 20px;
}

.result-display {
  margin-top: 20px;
}

.result-display h4 {
  font-size: 14px;
  margin: 0 0 15px 0;
  color: #606266;
}

.result-image img,
.result-video video {
  width: 100%;
  border-radius: 4px;
}

.result-text pre,
.result-json pre {
  background-color: #f5f7fa;
  padding: 15px;
  border-radius: 4px;
  border: 1px solid #e4e7ed;
  font-size: 13px;
  line-height: 1.5;
  overflow-x: auto;
  max-height: 300px;
  overflow-y: auto;
}

/* 响应式设计 */
@media (max-width: 1600px) {
  .left-sidebar {
    width: 250px;
  }
  
  .right-sidebar {
    width: 350px;
  }
}

@media (max-width: 1400px) {
  .left-sidebar {
    width: 200px;
  }
  
  .right-sidebar {
    width: 300px;
  }
}

/* 滚动条样式 */
::-webkit-scrollbar {
  width: 6px;
}

::-webkit-scrollbar-track {
  background: #f1f1f1;
}

::-webkit-scrollbar-thumb {
  background: #c1c1c1;
  border-radius: 3px;
}

::-webkit-scrollbar-thumb:hover {
  background: #a8a8a8;
}
</style>