<script>
export default {
  name: 'FileManagementPage'
}
</script>

<template>
  <div class="file-management-page">
    <!-- 工具栏 -->
    <div class="toolbar">
      <div class="toolbar-left">
        <button class="toolbar-btn toolbar-btn-primary" @click="refreshFileList">
          <i class="fas fa-sync-alt" :class="{ 'fa-spin': isLoading }"></i>
          <span>刷新列表</span>
        </button>
        <button
          class="toolbar-btn"
          :disabled="selectedFiles.length === 0"
          @click="downloadBatch"
        >
          <i class="fas fa-download"></i>
          <span>批量下载 ({{ selectedFiles.length }})</span>
        </button>
        <button
          class="toolbar-btn"
          :disabled="selectedFiles.length === 0"
          @click="openRenameModal"
        >
          <i class="fas fa-edit"></i>
          <span>批量重命名 ({{ selectedFiles.length }})</span>
        </button>
        <button
          class="toolbar-btn drop-target"
          @dragover.prevent="handleDragOver"
          @dragleave="handleDragLeave"
          @drop="handleDrop"
          title="将模型拖动到此处打开"
          :class="{ 'high-light': isDragOver }"
        >
          <i class="fas fa-folder-open"></i>
          <span>打开模型</span>
        </button>
      </div>
      <div class="toolbar-right">
        <button class="toolbar-btn" @click="openConfigModal" title="扫描配置">
           <i class="fas fa-cog"></i>
           <span>配置</span>
        </button>
        <div class="search-box">
          <i class="fas fa-search"></i>
          <input
            type="text"
            v-model="searchQuery"
            placeholder="搜索文件..."
          />
        </div>
      </div>
    </div>

    <!-- 文件列表区域 -->
    <div class="file-list-container">
      <table class="file-table">
        <thead>
          <tr>
            <th class="checkbox-col">
              <input
                type="checkbox"
                :checked="isAllSelected"
                @change="toggleSelectAll"
              />
            </th>
            <th>文件名</th>
            <th>路径</th>
            <th class="size-col">大小</th>
            <th class="ext-col">扩展名</th>
            <th class="time-col">修改时间</th>
            <th class="action-col">操作</th>
          </tr>
        </thead>
        <tbody>
          <tr v-if="isLoading && files.length === 0">
            <td colspan="7" class="loading-row">
              <div class="loading-spinner"></div>
              <span>加载中...</span>
            </td>
          </tr>
          <tr v-else-if="filteredFiles.length === 0">
            <td colspan="7" class="empty-row">
              <i class="fas fa-folder-open"></i>
              <span>暂无文件</span>
            </td>
          </tr>
          <tr
            v-else
            v-for="file in filteredFiles"
            :key="file.absolute_path"
            :class="{ selected: selectedFiles.includes(file.relative_path) }"
            draggable="true"
            @dragstart="handleDragStart($event, file)"
          >
            <td class="checkbox-col">
              <input
                type="checkbox"
                :checked="selectedFiles.includes(file.relative_path)"
                @change="toggleFileSelection(file.relative_path)"
              />
            </td>
            <td class="filename-cell">
              <i class="fas" :class="getFileIcon(file.extension)"></i>
              <span>{{ file.filename }}</span>
            </td>
            <td class="path-cell" :title="file.relative_path">{{ file.relative_path }}</td>
            <td class="size-cell">{{ formatFileSize(file.size) }}</td>
            <td><span class="file-tag">{{ file.extension }}</span></td>
            <td class="time-cell">{{ formatTime(file.modified_time) }}</td>
            <td class="action-cell">
              <button
                class="action-btn download"
                title="下载"
                @click="downloadFile(file)"
              >
                <i class="fas fa-download"></i>
              </button>
              <button
                class="action-btn rename"
                title="重命名"
                @click="openSingleRename(file)"
              >
                <i class="fas fa-edit"></i>
              </button>
            </td>
          </tr>
        </tbody>
      </table>
    </div>

    <!-- 底部状态栏 -->
    <div class="statusbar">
      <span>共 {{ filteredFiles.length }} 个文件</span>
      <span v-if="selectedFiles.length > 0">已选择 {{ selectedFiles.length }} 个</span>
      <span class="path-info">当前路径: {{ currentPath }}</span>
    </div>

    <!-- 配置弹窗 -->
    <div v-if="showConfigModal" class="modal-overlay" @click.self="closeConfigModal">
      <div class="modal-content config-modal-size">
        <div class="modal-header">
          <h3>文件扫描配置</h3>
          <button class="close-btn" @click="closeConfigModal">
            <i class="fas fa-times"></i>
          </button>
        </div>
        <div class="modal-body config-body">
           <!-- 路径设置 -->
           <section class="config-section">
              <h4>扫描目录</h4>
              <div class="form-group">
                <label>基础路径 (Base Path)</label>
                <input type="text" v-model="configBasePath" class="form-input" placeholder="例如: D:\CAD_Files">
                <p class="help-text">修改后将重新扫描该目录下的所有文件</p>
              </div>
           </section>

           <!-- 扩展名设置 -->
           <section class="config-section">
              <div class="section-header">
                <h4>文件类型扩展名</h4>
                <div class="add-category-wrapper">
                    <input 
                        type="text" 
                        v-model="newCategoryName" 
                        placeholder="新增分类 (如: excel)" 
                        class="small-input"
                        @keydown.enter.prevent="addNewCategory"
                    >
                    <button class="btn-small" @click="addNewCategory" :disabled="!newCategoryName">
                        <i class="fas fa-plus"></i>
                    </button>
                </div>
              </div>
              
              <div class="extensions-container">
                 <div v-if="Object.keys(configExtensions).length === 0" class="empty-tip">
                    暂无配置，请添加分类
                 </div>
                 <div v-for="(exts, category) in configExtensions" :key="category" class="extension-group">
                    <div class="group-header">
                       <span class="category-badge">{{ category }}</span>
                       <button class="btn-icon-danger" @click="removeCategory(category)" title="删除分类">
                           <i class="fas fa-trash-alt"></i>
                       </button>
                    </div>
                    <div class="tags-wrapper">
                       <span v-for="(ext, idx) in exts" :key="idx" class="ext-tag">
                          {{ ext }}
                          <i class="fas fa-times" @click="removeExtension(category, idx)"></i>
                       </span>
                       <div class="add-tag-box">
                          <input 
                            type="text" 
                            placeholder="+ .ext (回车)" 
                            @keydown.enter.prevent="addExtension(category, $event)"
                            @blur="addExtension(category, $event)"
                          >
                       </div>
                    </div>
                 </div>
              </div>
              <div v-if="isConfigLoading" class="config-loading-overlay">
                  <div class="loading-spinner"></div>
                  <span>读取配置中...</span>
              </div>
           </section>
        </div>
        <div class="modal-footer">
          <button class="btn-cancel" @click="closeConfigModal">取消</button>
          <button class="btn-confirm" @click="saveConfig">
            <i class="fas fa-save"></i> 保存配置
          </button>
        </div>
      </div>
    </div>

    <!-- 重命名弹窗 -->
    <div v-if="showRenameModal" class="modal-overlay" @click.self="closeRenameModal">
      <div class="modal-content">
        <div class="modal-header">
          <h3>文件批量重命名</h3>
          <button class="close-btn" @click="closeRenameModal">
            <i class="fas fa-times"></i>
          </button>
        </div>
        <div class="modal-body">
          <div class="rename-config">
             <div class="form-group">
                <label>重命名策略</label>
                <select v-model="selectedStrategy" class="form-select">
                  <option v-for="strategy in strategies" :key="strategy.name" :value="strategy.name">
                    {{ strategy.title }} - {{ strategy.description }}
                  </option>
                </select>
             </div>

             <!-- 策略参数表单 -->
             <div class="strategy-params">
                <!-- 添加前缀 -->
                <div v-if="selectedStrategy === 'add_prefix'" class="form-group">
                  <label>前缀文本</label>
                  <input type="text" v-model="renameParams.prefix" class="form-input" placeholder="请输入前缀...">
                </div>

                <!-- 添加后缀 -->
                <div v-if="selectedStrategy === 'add_suffix'" class="form-group">
                  <label>后缀文本</label>
                  <input type="text" v-model="renameParams.suffix" class="form-input" placeholder="请输入后缀...">
                </div>

                <!-- 序号重命名 -->
                <div v-if="selectedStrategy === 'sequence'" class="params-grid">
                  <div class="form-group">
                    <label>基础文件名</label>
                    <input type="text" v-model="renameParams.base_name" class="form-input" placeholder="例如: Part">
                  </div>
                  <div class="form-group">
                    <label>起始序号</label>
                    <input type="number" v-model.number="renameParams.start_number" class="form-input" min="1">
                  </div>
                   <div class="form-group">
                    <label>位数</label>
                    <input type="number" v-model.number="renameParams.digits" class="form-input" min="1" max="10">
                  </div>
                  <div class="form-group">
                    <label>分隔符</label>
                    <input type="text" v-model="renameParams.separator" class="form-input" style="width: 50px; text-align: center;">
                  </div>
                </div>

                <!-- 文本替换 -->
                <div v-if="selectedStrategy === 'replace_text'" class="params-grid">
                  <div class="form-group" style="flex: 1;">
                    <label>查找内容</label>
                    <input type="text" v-model="renameParams.search" class="form-input" placeholder="要查找的文本...">
                  </div>
                  <div class="form-group" style="flex: 1;">
                    <label>替换为</label>
                    <input type="text" v-model="renameParams.replace" class="form-input" placeholder="替换后的文本...">
                  </div>
                  <div class="form-group checkbox-group">
                     <label>
                       <input type="checkbox" v-model="renameParams.case_sensitive">
                       区分大小写
                     </label>
                  </div>
                </div>

                <!-- 添加时间 -->
                <div v-if="selectedStrategy === 'add_datetime'" class="params-grid">
                  <div class="form-group" style="flex: 2;">
                    <label>时间格式</label>
                    <input type="text" v-model="renameParams.format" class="form-input" placeholder="%Y%m%d_%H%M%S">
                  </div>
                   <div class="form-group" style="flex: 1;">
                    <label>位置</label>
                    <select v-model="renameParams.position" class="form-select">
                      <option value="prefix">前缀</option>
                      <option value="suffix">后缀</option>
                    </select>
                  </div>
                   <div class="form-group">
                    <label>分隔符</label>
                    <input type="text" v-model="renameParams.separator" class="form-input" style="width: 50px; text-align: center;">
                  </div>
                </div>

               <!-- 大小写转换 -->
               <div v-if="selectedStrategy === 'change_case'" class="form-group">
                  <label>转换方式</label>
                  <select v-model="renameParams.case_type" class="form-select">
                    <option value="lower">全部小写 (lowercase)</option>
                    <option value="upper">全部大写 (UPPERCASE)</option>
                    <option value="title">首字母大写 (Title Case)</option>
                  </select>
               </div>
             </div>
          </div>

          <div class="rename-preview">
            <h4>预览 ({{ previewList.length }} 个文件)</h4>
            <div class="preview-list">
              <div v-for="(item, index) in previewList" :key="index" class="preview-item">
                 <div class="preview-original" :title="item.original">{{ item.original }}</div>
                 <i class="fas fa-arrow-right"></i>
                 <div class="preview-new" :title="item.new" :class="{ 'text-changed': item.original !== item.new }">{{ item.new }}</div>
              </div>
            </div>
          </div>
        </div>
        <div class="modal-footer">
          <button class="btn-cancel" @click="closeRenameModal">取消</button>
          <button class="btn-confirm" @click="applyRename">
            <i class="fas fa-check"></i> 确认重命名
          </button>
        </div>
      </div>
    </div>
  </div>
</template>

<script setup>
import { ref, computed, onMounted, onUnmounted, watch } from 'vue'
import { websocketService } from '@/services/websocketService'
import { getWebSocketConfig } from '@/config/cad'
import { useCADStore } from '@/stores/cad'
import creoApi from '@/services/creoApi'
import revitApi from '@/services/revitApi'

const cadStore = useCADStore()

// 状态
const files = ref([])
const selectedFiles = ref([])
const isLoading = ref(false)
const searchQuery = ref('')
const currentPath = ref('C:\\Users\\Public\\Documents')
const showRenameModal = ref(false)
const selectedStrategy = ref('add_prefix')
const renameParams = ref({
  prefix: 'NEW_',
  suffix: '_backup',
  base_name: 'Part',
  start_number: 1,
  digits: 3,
  separator: '_',
  search: '',
  replace: '',
  case_sensitive: true,
  format: '%Y%m%d',
  position: 'suffix',
  position: 'suffix',
  case_type: 'lower'
})

// 配置相关状态
const showConfigModal = ref(false)
const configBasePath = ref('')
const configExtensions = ref({})
const newCategoryName = ref('')
const isConfigLoading = ref(false)

// 拖拽相关状态
const isDragOver = ref(false)

// 策略定义
const strategies = ref([
  { name: 'add_prefix', title: '添加前缀', description: '在文件名前添加字符' },
  { name: 'add_suffix', title: '添加后缀', description: '在扩展名前添加字符' },
  { name: 'sequence', title: '序列化重命名', description: '使用数字序列重命名' },
  { name: 'replace_text', title: '文本替换', description: '替换文件名中的指定文本' },
  { name: 'add_datetime', title: '添加时间戳', description: '添加时间信息' },
  { name: 'change_case', title: '大小写转换', description: '更改文件名大小写' }
])



// 过滤后的文件列表
const filteredFiles = computed(() => {
  if (!searchQuery.value) return files.value
  const query = searchQuery.value.toLowerCase()
  return files.value.filter(file =>
    file.filename.toLowerCase().includes(query) ||
    file.relative_path.toLowerCase().includes(query)
  )
})

// 是否全选
const isAllSelected = computed(() => {
  return filteredFiles.value.length > 0 &&
         selectedFiles.value.length === filteredFiles.value.length
})

// 预览列表计算属性
const previewList = ref([])

// 更新预览
const updatePreview = () => {
    if (!showRenameModal.value) return
    const targets = selectedFiles.value
    if (targets.length === 0) return

    websocketService.previewRename(
        targets,
        selectedStrategy.value,
        renameParams.value
    )
}

// 监听参数变化自动更新预览
watch([selectedStrategy, renameParams, selectedFiles], () => {
    // 防抖处理
    if (previewTimer) clearTimeout(previewTimer)
    previewTimer = setTimeout(updatePreview, 500)
}, { deep: true })

let previewTimer = null

// 辅助函数：分割文件名和扩展名 (处理 .prt.1 这种复杂后缀)
function splitFilename(filename) {
  // 简单处理：取第一个点前的作为基础名，其余作为扩展名
  // 更严谨的处理需要根据业务逻辑，这里为了通用性处理
  const firstDotIndex = filename.indexOf('.')
  if (firstDotIndex === -1) return [filename, '']
  return [filename.substring(0, firstDotIndex), filename.substring(firstDotIndex)]
}

function escapeRegExp(string) {
  return string.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
}



// WebSocket 事件处理
const handleFileListUpdate = (data) => {
  if (data.files) {
    files.value = data.files
    currentPath.value = data.base_path || currentPath.value
  }
  isLoading.value = false
}

const handleDownloadUrl = (data) => {
  const wsConfig = getWebSocketConfig()
  const HTTP_BASE_URL = wsConfig.BASE_URL.replace('ws://', 'http://').replace('wss://', 'https://')

  if (data.download_url) {
    if (data.method === 'POST') {
      // 批量下载
      fetch(`${HTTP_BASE_URL}${data.download_url}`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify(data.file_paths) // 假设后端在response里把paths传回来了，或者我们需要在前端保存
        // API文档说响应包含file_paths
      })
      .then(response => response.blob())
      .then(blob => {
        const url = window.URL.createObjectURL(blob);
        const a = document.createElement('a');
        a.href = url;
        a.download = 'cad_files.zip';
        a.click();
        window.URL.revokeObjectURL(url);
      })
      .catch(error => console.error('批量下载失败:', error))
    } else {
      // 单文件下载
      const fullUrl = `${HTTP_BASE_URL}${data.download_url}`
      window.open(fullUrl, '_blank')
    }
  }
}

const handleRenameStrategies = (strategyList) => {
    if (strategyList && strategyList.length > 0) {
        const titleMap = {
          'add_prefix': '添加前缀',
          'add_suffix': '添加后缀',
          'sequence': '序列化重命名',
          'replace_text': '文本替换',
          'add_datetime': '添加时间戳',
          'change_case': '大小写转换'
        }
        
        strategies.value = strategyList.map(s => ({ 
            ...s, 
            title: titleMap[s.name] || s.name 
        }))
    }
}

const handleRenamePreview = (data) => {
    if (data.preview) {
        previewList.value = data.preview
    }
}

const handleRenameResult = (data) => {
    if (data.success_count !== undefined) {
        alert(`重命名完成: 成功 ${data.success_count}, 失败 ${data.failed_count}`)
        closeRenameModal()
        refreshFileList()
    }
}


// 初始化
onMounted(() => {
  // 注册监听器
  websocketService.on('onFileListUpdate', handleFileListUpdate)
  websocketService.on('onDownloadUrl', handleDownloadUrl)
  websocketService.on('onRenameStrategies', handleRenameStrategies)
  websocketService.on('onRenamePreview', handleRenamePreview)
  websocketService.on('onRenameResult', handleRenameResult)
  websocketService.on('onFileConfigUpdate', handleFileConfigUpdate)

  // 初始获取
  refreshFileList()
  
  // 获取初始配置
  websocketService.getFileConfig()
  websocketService.getRenameStrategies()
})

onUnmounted(() => {
  // 注销监听器
  websocketService.off('onFileListUpdate', handleFileListUpdate)
  websocketService.off('onDownloadUrl', handleDownloadUrl)
  websocketService.off('onRenameStrategies', handleRenameStrategies)
  websocketService.off('onRenamePreview', handleRenamePreview)
  websocketService.off('onRenameResult', handleRenameResult)
  websocketService.off('onFileConfigUpdate', handleFileConfigUpdate)
})

// 获取文件图标
const getFileIcon = (ext) => {
  if (ext.includes('.prt') || ext.includes('.asm')) return 'fa-cube text-blue'
  if (ext.includes('.rvt') || ext.includes('.rfa')) return 'fa-building text-green'
  if (ext.includes('.rvm')) return 'fa-industry text-orange'
  if (ext.includes('.drw') || ext.includes('.dri')) return 'fa-file-alt text-gray'
  return 'fa-file text-gray'
}

// 格式化文件大小
const formatFileSize = (bytes) => {
  if (bytes === 0) return '0 B'
  const k = 1024
  const sizes = ['B', 'KB', 'MB', 'GB', 'TB']
  const i = Math.floor(Math.log(bytes) / Math.log(k))
  return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i]
}

// 格式化时间
const formatTime = (timestamp) => {
  return new Date(timestamp * 1000).toLocaleString()
}

// 刷新列表
const refreshFileList = () => {
  isLoading.value = true
  files.value = [] // 清空当前列表
  websocketService.getFileList()
}

// 切换选择
const toggleFileSelection = (path) => {
  const index = selectedFiles.value.indexOf(path)
  if (index === -1) {
    selectedFiles.value.push(path)
  } else {
    selectedFiles.value.splice(index, 1)
  }
}

// 全选/反选
const toggleSelectAll = () => {
  if (isAllSelected.value) {
    selectedFiles.value = []
  } else {
    selectedFiles.value = filteredFiles.value.map(f => f.relative_path)
  }
}

// 下载文件
const downloadFile = (file) => {
  websocketService.downloadFile(file.relative_path)
}

// 批量下载
const downloadBatch = () => {
  websocketService.downloadBatch(selectedFiles.value)
}

// 单个重命名
const openSingleRename = (file) => {
    selectedFiles.value = [file.relative_path]
    openRenameModal()
}

// 打开重命名弹窗
const openRenameModal = () => {
  showRenameModal.value = true
}

// 关闭重命名弹窗
const closeRenameModal = () => {
  showRenameModal.value = false
}

// 应用重命名
const applyRename = () => {
  websocketService.renameFiles(
      selectedFiles.value,
      selectedStrategy.value,
      renameParams.value
  )
}

// 处理配置更新
const handleFileConfigUpdate = (data) => {
  isConfigLoading.value = false
  if (data.base_path) {
    configBasePath.value = data.base_path
    // 如果是设置成功后的回传，更新当前路径
    if (showConfigModal.value === false) { 
       currentPath.value = data.base_path
    }
  }
  if (data.file_extensions) {
    configExtensions.value = JSON.parse(JSON.stringify(data.file_extensions))
  }
}

// 配置模态框方法
const openConfigModal = () => {
  isConfigLoading.value = true
  showConfigModal.value = true
  
  // 尝试发送请求
  const sent = websocketService.getFileConfig() 
  
  if (!sent) {
      // 发送失败（未连接），直接结束加载状态
      isConfigLoading.value = false
      // 但我们仍然显示弹窗，允许用户看（虽然可能是空的）或者手动重试?
      // 更好的是提示用户
      // 这里简单处理：让它保持打开，但 loading 结束
  } else {
      // 设置超时保护 (3秒后如果还没响应，就停止loading)
      setTimeout(() => {
          if (isConfigLoading.value) {
              isConfigLoading.value = false
          }
      }, 3000)
  }
}

const closeConfigModal = () => {
  showConfigModal.value = false
  isConfigLoading.value = false
}

const removeExtension = (category, index) => {
    if (configExtensions.value[category]) {
        configExtensions.value[category].splice(index, 1)
    }
}

const removeCategory = (category) => {
    if (confirm(`确定要删除 "${category}" 分类及其所有后缀吗？`)) {
        delete configExtensions.value[category]
    }
}

const addNewCategory = () => {
    const name = newCategoryName.value.trim()
    if (!name) return
    
    if (configExtensions.value[name]) {
        alert('该分类已存在')
        return
    }
    
    // Use standard reactivity assignment for new property
    configExtensions.value = {
        ...configExtensions.value,
        [name]: []
    }
    newCategoryName.value = ''
}

const addExtension = (category, event) => {
    const val = event.target.value.trim()
    if (!val) return
    
    // Ensure starts with .
    const ext = val.startsWith('.') ? val : `.${val}`
    
    if (!configExtensions.value[category]) {
        configExtensions.value[category] = []
    }
    
    if (!configExtensions.value[category].includes(ext)) {
        configExtensions.value[category].push(ext)
    }
    
    event.target.value = '' // clear input
}

const saveConfig = () => {
    // 验证: 检查是否有分类但没有后缀的情况
    for (const [category, exts] of Object.entries(configExtensions.value)) {
        if (!exts || exts.length === 0) {
            alert(`分类 "${category}" 下没有添加任何扩展名 (如 .md, .txt)，将无法扫描到文件。请先添加扩展名。`)
            return
        }
    }

    // 保存路径
    if (configBasePath.value) {
        websocketService.setBasePath(configBasePath.value)
    }
    
    // 保存扩展名
    websocketService.setFileExtensions(configExtensions.value)
    
    closeConfigModal()
    
    // 延迟刷新列表 (给后端一点时间保存和重新扫描)
    setTimeout(() => {
        refreshFileList()
    }, 500)
}

// 拖拽处理
const handleDragStart = (event, file) => {
  console.log('拖拽开始:', file.filename)
  
  // 必须先设置 effectAllowed
  event.dataTransfer.effectAllowed = 'copy'
  
  const payload = {
    filePath: file.absolute_path,
    filename: file.filename,
    extension: file.extension
  }
  
  try {
    const jsonPayload = JSON.stringify(payload)
    // 优先设置标准MIME类型
    event.dataTransfer.setData('application/json', jsonPayload)
    // 兼容文本类型
    event.dataTransfer.setData('text/plain', jsonPayload)
    
    console.log('Drag data set:', jsonPayload)
  } catch (e) {
    console.error('设置拖拽数据失败', e)
  }
}

// 注意：handleDragOver 在这里主要处理放入文件列表的情况（如果有），
// 但主要目标是 Drop 到 Sidebar。这里保留是为了防止自身互相拖拽产生副作用
const handleDragOver = (event) => {
  event.preventDefault()
  event.dataTransfer.dropEffect = 'copy'
  isDragOver.value = true
}

const handleDragLeave = (event) => {
  isDragOver.value = false
}

const handleDrop = (event) => {
  isDragOver.value = false
  const data = event.dataTransfer.getData('application/json')
  
  if (!data) return

  try {
    const fileInfo = JSON.parse(data)
    openModel(fileInfo)
  } catch (e) {
    console.error('解析拖拽数据失败', e)
  }
}

// 打开模型逻辑
const openModel = async (fileInfo) => {
  // 1. 检查是否连接了 CAD 软件
  if (!cadStore.currentCAD) {
    alert('请先连接相关的CAD软件（如Creo）才可以打开模型。')
    return
  }

  const currentCADId = cadStore.currentCAD.id

  // 2. 根据连接的软件类型判断
  if (currentCADId === 'creo') {
    // Creo: 发送打开命令到本地插件 API
    try {
      const result = await creoApi.openModelFile(fileInfo.filePath)
      if (result && result.success) {
         // 可以在这里添加成功提示，或者apiClient已经处理了
         console.log(`Creo打开模型成功: ${fileInfo.filename}`)
      } else {
         console.error('Creo打开模型失败', result)
      }
    } catch (error) {
      console.error('调用Creo打开接口异常', error)
      alert(`打开模型失败: ${error.message}`)
    }
  } else if (currentCADId === 'revit') {
    // Revit: 发送打开命令到本地插件 API
    try {
      const result = await revitApi.openModelFile(fileInfo.filePath, false)
      if (result && result.success) {
         console.log(`Revit打开模型成功: ${fileInfo.filename}`)
      } else {
         console.error('Revit打开模型失败', result)
      }
    } catch (error) {
      console.error('调用Revit打开接口异常', error)
      alert(`打开模型失败: ${error.message}`)
    }
  } else {
    // 3. 其他软件: 占位提示
    alert(`当前连接的是 ${cadStore.currentCAD.name}，该软件的打开模型接口尚未实现（仅支持Creo和Revit）。`)
  }
}

</script>

<style scoped>
/* 文件列表表格样式修正 */
.file-table tr[draggable="true"] {
  cursor: grab;
  user-select: none; /* 防止选中文字影响拖拽 */
}

.file-table tr[draggable="true"]:active {
  cursor: grabbing;
}

.file-management-page {
  height: 100%;
  display: flex;
  flex-direction: column;
  background: var(--color-bg-primary);
  color: var(--color-text-primary);
}

/* 工具栏 */
.toolbar {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: var(--spacing-lg);
  background: var(--color-bg-secondary);
  border-bottom: 1px solid var(--color-border-primary);
}

.toolbar-left, .toolbar-right {
  display: flex;
  align-items: center;
  gap: var(--spacing-md);
}

.toolbar-btn {
  display: flex;
  align-items: center;
  gap: var(--spacing-sm);
  padding: var(--spacing-sm) var(--spacing-lg);
  background: var(--color-bg-tertiary);
  border: 1px solid var(--color-border-primary);
  border-radius: var(--size-border-radius-button);
  color: var(--color-text-primary);
  cursor: pointer;
  transition: var(--transition-all);
  font-size: var(--font-size-base);
}

.toolbar-btn.drop-target {
  border-style: dashed;
  border-width: 2px;
  background: rgba(var(--color-primary-rgb), 0.05);
  transition: all 0.2s ease;
}

.toolbar-btn.drop-target.high-light {
  background: rgba(var(--color-primary-rgb), 0.2);
  border-color: var(--color-primary);
  transform: scale(1.05);
  box-shadow: 0 0 10px rgba(var(--color-primary-rgb), 0.3);
}

.toolbar-btn:hover:not(:disabled) {
  background: var(--color-bg-hover);
  border-color: var(--color-primary);
  transform: translateY(-1px);
}

.config-loading-overlay {
    position: absolute;
    top: 60px; /* Skip header */
    left: 0;
    right: 0;
    bottom: 60px; /* Skip footer */
    background: rgba(var(--color-bg-primary-rgb), 0.7);
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    z-index: 10;
    backdrop-filter: blur(2px);
    gap: var(--spacing-md);
    color: var(--color-primary);
}

.toolbar-btn:disabled {
  opacity: 0.5;
  cursor: not-allowed;
}

.toolbar-btn-primary {
  background: var(--color-primary-gradient);
  border-color: transparent;
  color: white;
}

.toolbar-btn-primary:hover:not(:disabled) {
  background: var(--color-primary-gradient-hover);
  box-shadow: 0 4px 15px var(--color-primary-rgb-3);
}

.search-box {
  display: flex;
  align-items: center;
  background: var(--color-bg-tertiary);
  border: 1px solid var(--color-border-primary);
  border-radius: var(--size-border-radius);
  padding: var(--spacing-xs) var(--spacing-md);
  width: 250px;
}

.search-box i {
  color: var(--color-text-tertiary);
  margin-right: var(--spacing-sm);
}

.search-box input {
  background: transparent;
  border: none;
  color: var(--color-text-primary);
  width: 100%;
  outline: none;
  font-size: var(--font-size-base);
}

/* 文件列表 */
.file-list-container {
  flex: 1;
  overflow: auto;
  padding: var(--spacing-md);
}

.file-table {
  width: 100%;
  border-collapse: separate;
  border-spacing: 0;
  color: var(--color-text-primary);
}

.file-table th {
  text-align: left;
  padding: var(--spacing-md);
  background: var(--color-bg-tertiary);
  font-weight: 600;
  border-bottom: 1px solid var(--color-border-primary);
  position: sticky;
  top: 0;
  z-index: 10;
}

.file-table td {
  padding: var(--spacing-md);
  border-bottom: 1px solid var(--color-border-primary);
  vertical-align: middle;
}

.file-table tr:hover {
  background: var(--color-bg-hover);
}

.file-table tr.selected {
  background: rgba(var(--color-primary-rgb), 0.1);
}

.checkbox-col {
  width: 40px;
  text-align: center;
}

.size-col {
  width: 100px;
}

.ext-col {
  width: 100px;
}

.time-col {
  width: 180px;
}

.action-col {
  width: 120px;
  text-align: center;
}

.filename-cell {
  display: flex;
  align-items: center;
  gap: var(--spacing-md);
  font-weight: 500;
}

.filename-cell i {
  font-size: var(--font-size-lg);
}

.path-cell {
  color: var(--color-text-secondary);
  font-size: var(--font-size-sm);
  max-width: 300px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.size-cell, .time-cell {
  color: var(--color-text-secondary);
  font-size: var(--font-size-sm);
}

.file-tag {
  display: inline-block;
  padding: 2px 8px;
  background: var(--color-bg-tertiary);
  border: 1px solid var(--color-border-primary);
  border-radius: 4px;
  font-size: 12px;
  font-family: monospace;
}

/* 操作按钮 */
.action-cell {
  white-space: nowrap;
}

.action-btn {
  background: transparent;
  border: none;
  color: var(--color-text-secondary);
  cursor: pointer;
  padding: 6px;
  margin: 0 4px;
  border-radius: 4px;
  transition: all 0.2s;
}

.action-btn:hover {
  background: var(--color-bg-tertiary);
  color: var(--color-primary);
}

.action-btn.download:hover {
  color: var(--color-success);
}

.action-btn.rename:hover {
  color: var(--color-warning);
}

/* 状态栏 */
.statusbar {
  padding: var(--spacing-sm) var(--spacing-lg);
  background: var(--color-bg-secondary);
  border-top: 1px solid var(--color-border-primary);
  display: flex;
  gap: var(--spacing-xl);
  font-size: var(--font-size-sm);
  color: var(--color-text-secondary);
}

.path-info {
  margin-left: auto;
  font-family: monospace;
}

/* 图标颜色辅助类 */
.text-blue { color: #3b82f6; }
.text-green { color: #10b981; }
.text-orange { color: #f59e0b; }
.text-gray { color: #9ca3af; }

/* 加载和空状态 */
.loading-row, .empty-row {
  text-align: center;
  padding: var(--spacing-4xl) !important;
  color: var(--color-text-tertiary);
}

.loading-spinner {
  display: inline-block;
  width: 24px;
  height: 24px;
  border: 3px solid rgba(255,255,255,0.3);
  border-radius: 50%;
  border-top-color: var(--color-primary);
  animation: spin 1s ease-in-out infinite;
  margin-bottom: var(--spacing-sm);
  vertical-align: middle;
  margin-right: var(--spacing-sm);
}

@keyframes spin {
  to { transform: rotate(360deg); }
}

.empty-row i {
  display: block;
  font-size: 48px;
  margin-bottom: var(--spacing-md);
  opacity: 0.5;
}

/* Modal Styling */
.modal-overlay {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background: rgba(0, 0, 0, 0.5);
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 1000;
  backdrop-filter: blur(4px);
}

.modal-content {
  background: var(--color-bg-primary);
  border-radius: var(--size-border-radius-lg);
  width: 800px;
  max-width: 90%;
  max-height: 85vh;
  display: flex;
  flex-direction: column;
  box-shadow: 0 10px 40px rgba(0,0,0,0.3);
  border: 1px solid var(--color-border-primary);
}

.modal-header {
  padding: var(--spacing-lg);
  border-bottom: 1px solid var(--color-border-primary);
  display: flex;
  align-items: center;
  justify-content: space-between;
}

.modal-header h3 {
  margin: 0;
  font-size: var(--font-size-xl);
  color: var(--color-text-primary);
}

.close-btn {
  background: transparent;
  border: none;
  color: var(--color-text-tertiary);
  font-size: var(--font-size-lg);
  cursor: pointer;
  transition: color 0.2s;
}

.close-btn:hover {
  color: var(--color-text-primary);
}

.modal-body {
  padding: var(--spacing-xl);
  overflow-y: auto;
  display: flex;
  gap: var(--spacing-xl);
}

.rename-config {
  flex: 1;
  min-width: 300px;
}

.rename-preview {
  flex: 1;
  background: var(--color-bg-tertiary);
  border-radius: var(--size-border-radius);
  padding: var(--spacing-md);
  border: 1px solid var(--color-border-primary);
  display: flex;
  flex-direction: column;
  min-height: 300px;
  overflow: hidden;
}

.rename-preview h4 {
  margin: 0 0 var(--spacing-md) 0;
  font-size: var(--font-size-base);
  color: var(--color-text-secondary);
}

.preview-list {
  flex: 1;
  overflow-y: auto;
  padding-right: var(--spacing-sm);
}

.preview-item {
  display: flex;
  align-items: center;
  gap: var(--spacing-md);
  padding: var(--spacing-xs) 0;
  font-size: var(--font-size-sm);
  border-bottom: 1px dashed var(--color-border-secondary);
}

.preview-item:last-child {
  border-bottom: none;
}

.preview-original {
  color: var(--color-text-secondary);
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.preview-item i {
  color: var(--color-text-tertiary);
  font-size: 10px;
}

.preview-new {
  color: var(--color-text-primary);
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  font-weight: 500;
}

.preview-new.text-changed {
  color: var(--color-success);
}

.form-group {
  margin-bottom: var(--spacing-lg);
}

.form-group label {
  display: block;
  margin-bottom: var(--spacing-sm);
  color: var(--color-text-secondary);
  font-size: var(--font-size-sm);
}

.form-select, .form-input {
  width: 100%;
  padding: var(--spacing-sm) var(--spacing-md);
  background: var(--color-bg-secondary);
  border: 1px solid var(--color-border-primary);
  border-radius: var(--size-border-radius);
  color: var(--color-text-primary);
  font-size: var(--font-size-base);
  outline: none;
  transition: border-color 0.2s;
}

.form-select:focus, .form-input:focus {
  border-color: var(--color-primary);
}

.params-grid {
  display: flex;
  gap: var(--spacing-md);
}

.checkbox-group {
  display: flex;
  align-items: center;
  height: 100%;
  padding-top: 24px;
}

.checkbox-group label {
  display: flex;
  align-items: center;
  gap: var(--spacing-sm);
  cursor: pointer;
  margin: 0;
}

.modal-footer {
  padding: var(--spacing-lg);
  border-top: 1px solid var(--color-border-primary);
  display: flex;
  justify-content: flex-end;
  gap: var(--spacing-md);
}

.btn-cancel, .btn-confirm {
  padding: var(--spacing-sm) var(--spacing-xl);
  border-radius: var(--size-border-radius-button);
  font-size: var(--font-size-base);
  cursor: pointer;
  transition: all 0.2s;
}

.btn-cancel {
  background: transparent;
  border: 1px solid var(--color-border-primary);
  color: var(--color-text-primary);
}

.btn-cancel:hover {
  background: var(--color-bg-secondary);
}

.btn-confirm {
  background: var(--color-primary-gradient);
  border: none;
  color: white;
  display: flex;
  align-items: center;
  gap: var(--spacing-sm);
}

.btn-confirm:hover {
  background: var(--color-primary-gradient-hover);
  box-shadow: 0 4px 15px var(--color-primary-rgb-3);
  transform: translateY(-1px);
}

/* Config Modal Styles */
.config-modal-size {
    width: 600px;
}

.config-body {
    flex-direction: column;
    gap: var(--spacing-sm);
}

.config-section {
    margin-bottom: var(--spacing-lg);
}


.config-section h4 {
    margin: 0;
    color: var(--color-primary);
    font-size: var(--font-size-lg);
}

.section-header {
    display: flex;
    justify-content: space-between;
    align-items: center;
    margin-bottom: var(--spacing-md);
    padding-bottom: var(--spacing-xs);
    border-bottom: 2px solid var(--color-bg-secondary);
}

.add-category-wrapper {
    display: flex;
    gap: var(--spacing-xs);
}

.small-input {
    padding: 2px 8px;
    border-radius: 4px;
    border: 1px solid var(--color-border-primary);
    background: var(--color-bg-tertiary);
    color: var(--color-text-primary);
    font-size: 12px;
    width: 120px;
}

.btn-small {
    padding: 2px 6px;
    background: var(--color-bg-tertiary);
    border: 1px solid var(--color-border-primary);
    border-radius: 4px;
    color: var(--color-success);
    cursor: pointer;
}

.btn-small:hover {
    border-color: var(--color-success);
    background: rgba(var(--color-success-rgb), 0.1);
}

.btn-icon-danger {
    background: transparent;
    border: none;
    color: var(--color-text-tertiary);
    cursor: pointer;
    font-size: 12px;
    padding: 4px;
    transition: color 0.2s;
}

.btn-icon-danger:hover {
    color: #ef4444;
}

.help-text {
    font-size: var(--font-size-xs);
    color: var(--color-text-tertiary);
    margin-top: 4px;
}

.extensions-container {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-md);
    max-height: 400px;
    overflow-y: auto;
}

.empty-tip {
    text-align: center;
    color: var(--color-text-tertiary);
    padding: var(--spacing-lg);
    font-size: var(--font-size-sm);
    border: 1px dashed var(--color-border-secondary);
    border-radius: var(--size-border-radius);
}

.extension-group {
    background: var(--color-bg-secondary);
    padding: var(--spacing-md);
    border-radius: var(--size-border-radius);
    border: 1px solid var(--color-border-secondary);
}

.group-header {
    margin-bottom: var(--spacing-sm);
    display: flex;
    justify-content: space-between;
    align-items: center;
}

.category-badge {
    background: var(--color-primary);
    color: white;
    padding: 2px 8px;
    border-radius: 4px;
    font-size: 12px;
    text-transform: uppercase;
    font-weight: 600;
}

.tags-wrapper {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
    align-items: center;
}

.ext-tag {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    background: var(--color-bg-tertiary);
    border: 1px solid var(--color-border-primary);
    padding: 4px 8px;
    border-radius: 4px;
    font-family: monospace;
    font-size: 13px;
    color: var(--color-text-primary);
}

.ext-tag:hover {
    border-color: var(--color-primary);
}

.ext-tag i {
    cursor: pointer;
    color: var(--color-text-tertiary);
    font-size: 11px;
    transition: color 0.2s;
}

.ext-tag i:hover {
    color: var(--color-danger, #ef4444);
}

.add-tag-box input {
    width: 60px;
    background: transparent;
    border: 1px dashed var(--color-border-primary);
    color: var(--color-text-secondary);
    font-size: 12px;
    padding: 4px;
    border-radius: 4px;
    text-align: center;
    outline: none;
    transition: all 0.2s;
}

.add-tag-box input:focus {
    width: 80px;
    border-color: var(--color-primary);
    border-style: solid;
    color: var(--color-text-primary);
}
</style>
