<template>
  <div class="xlsx-preview">
    <!-- 加载状态 -->
    <div v-if="loading" class="loading">
      <div class="spinner"></div>
      <p>正在加载Excel文件...</p>
    </div>

    <!-- 错误信息 -->
    <div v-if="error" class="error">{{ error }}</div>

    <!-- Excel内容展示 -->
    <div v-if="workbook" class="workbook-container">
      <!-- 工作表标签 -->
      <div class="sheet-tabs">
        <button v-for="(sheet, index) in workbook.SheetNames" :key="index"
          :class="{ active: activeSheetIndex === index }" @click="activeSheetIndex = index">
          {{ sheet }}
        </button>
      </div>

      <!-- 表格内容区域 -->
      <div class="sheet-content">
        <table v-if="activeSheetData">
          <tbody>
            <tr v-for="(row, rowIndex) in activeSheetData" :key="rowIndex">
              <td v-for="(cell, colIndex) in row" :key="colIndex" :class="{
                'header-cell': rowIndex === 0,
                'odd-row': rowIndex % 2 === 1
              }">
                {{ cell || '' }}
              </td>
            </tr>
          </tbody>
        </table>
      </div>
    </div>
  </div>
</template>

<script>
import * as XLSX from 'xlsx';

export default {
  name: "XlsxPreview",
  props: {
    src: {
      type: String,
      required: true,
      description: "Excel文件的URL或路径"
    }
  },
  data () {
    return {
      workbook: null,       // 解析后的Excel工作簿
      activeSheetIndex: 0,  // 当前激活的工作表索引
      loading: false,       // 加载状态
      error: null           // 错误信息
    };
  },
  watch: {
    src: {
      immediate: true,
      handler () {
        this.loadAndParseExcel();
      }
    }
  },
  computed: {
    // 获取当前激活的工作表数据
    activeSheetData () {
      if (!this.workbook || !this.workbook.SheetNames.length) return null;

      const sheetName = this.workbook.SheetNames[this.activeSheetIndex];
      const worksheet = this.workbook.Sheets[sheetName];

      // 将工作表转换为二维数组
      return XLSX.utils.sheet_to_json(worksheet, { header: 1 });
    }
  },
  methods: {
    /**
     * 加载并解析Excel文件
     */
    async loadAndParseExcel () {
      this.loading = true;
      this.error = null;
      this.workbook = null;

      try {
        // 验证URL格式
        if (!this.src || (this.src.startsWith('http') && !this.isValidUrl(this.src))) {
          throw new Error('无效的文件路径');
        }

        // 加载文件
        const response = await fetch(this.src);
        if (!response.ok) {
          throw new Error(`加载失败: ${response.status} ${response.statusText}`);
        }

        // 转换为ArrayBuffer
        const arrayBuffer = await response.arrayBuffer();

        // 解析Excel
        this.workbook = XLSX.read(arrayBuffer, {
          type: 'array',
          cellDates: true,    // 解析日期类型
          cellText: false     // 保持单元格原始类型
        });

        // 重置到第一个工作表
        this.activeSheetIndex = 0;
      } catch (err) {
        this.error = err.message;
        console.error('Excel处理错误:', err);
      } finally {
        this.loading = false;
      }
    },

    /**
     * 验证URL格式
     */
    isValidUrl (url) {
      try {
        new URL(url);
        return true;
      } catch (e) {
        return false;
      }
    }
  }
};
</script>

<style scoped>
.xlsx-preview {
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
  border: 1px solid #e5e7eb;
  border-radius: 6px;
  overflow: hidden;
  width: 100%;
  height: 100%;
}

/* 加载状态样式 */
.loading {
  padding: 40px 20px;
  text-align: center;
  color: #6b7280;
}

.spinner {
  width: 40px;
  height: 40px;
  margin: 0 auto 16px;
  border: 4px solid #e5e7eb;
  border-top-color: #3b82f6;
  border-radius: 50%;
  animation: spin 1s linear infinite;
}

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

/* 错误信息样式 */
.error {
  padding: 20px;
  color: #dc2626;
  background-color: #fee2e2;
  border-bottom: 1px solid #fecaca;
}

/* 工作表标签样式 */
.sheet-tabs {
  display: flex;
  background-color: #f9fafb;
  border-bottom: 1px solid #e5e7eb;
  overflow-x: auto;
  white-space: nowrap;
}

.sheet-tabs button {
  padding: 8px 16px;
  border: none;
  background: none;
  font-size: 14px;
  color: #4b5563;
  cursor: pointer;
  border-bottom: 2px solid transparent;
  transition: all 0.2s;
}

.sheet-tabs button:hover:not(.active) {
  background-color: #f3f4f6;
  color: #1f2937;
}

.sheet-tabs button.active {
  border-bottom-color: #3b82f6;
  color: #3b82f6;
  font-weight: 500;
}

/* 表格内容样式 */
.sheet-content {
  overflow: auto;
  max-height: 600px;
}

table {
  width: 100%;
  border-collapse: collapse;
  min-width: max-content;
}

td {
  padding: 8px 12px;
  border: 1px solid #e5e7eb;
  min-width: 80px;
  font-size: 14px;
  color: #1f2937;
}

.header-cell {
  background-color: #f3f4f6;
  font-weight: 500;
  color: #111827;
}

.odd-row {
  background-color: #f9fafb;
}
</style>