<script setup lang="ts">
import { ref, computed, watch } from "vue";
import { useRoute } from "vue-router";
import type { TableInstance } from "element-plus";

// Props 定义
const props = defineProps({
  title: {
    type: String,
    default: "列表选择",
  },
  // 表格数据
  tableData: {
    type: Array as () => any[],
    default: () => [],
  },
  // 是否显示加载状态
  loading: {
    type: Boolean,
    default: false,
  },
  // 用于行勾选的唯一键，默认 'id'
  rowKey: {
    type: String,
    default: "id",
  },
  // 是否默认全选（可选）
  defaultSelectAll: {
    type: Boolean,
    default: false,
  },
  // 新增：是否显示底部统计信息
  showSummary: {
    type: Boolean,
    default: true,
  },
  // 新增：自定义统计文本前缀，默认 "共"
  summaryText: {
    type: String,
    default: "共",
  },
  // 【新增】是否禁用所有行的选中功能
  // true: 所有行不可选 (复选框变灰)
  // false: 所有行可选 (默认)
  disabledSelection: {
    type: Boolean,
    default: false,
  },
  useAuth: {
    type: Boolean,
    default: true,
  },
  selectable: {
    type: Boolean,
    default: true,
  },
});

const visible = defineModel<boolean>("visible");

// Emits 定义
const emit = defineEmits<{
  "update:visible": [value: boolean];
  "selection-change": [selection: any[]];
  "dialog-button-click": [eventName: string, buttonConfig: globalThis.ButtonProp, selectedRows: any[]];
  "filter-refresh": []; // 当父组件在 slot 中点击查询时，可触发此事件刷新数据
}>();

const route = useRoute();
const tableRef = ref<TableInstance>();

// 获取底部对话框按钮权限
// 假设权限数据结构与参考代码类似，但来源是 dialogButtonAuth
const dialogButtonList = computed<globalThis.ButtonProp[]>(() => {
  if (!props.useAuth) return [];
  const list = (route.meta.dialogButtonAuth as globalThis.ButtonProp[]) || [];
  // 按 rank 排序，rank 越小越靠前，没有 rank 的排后面
  return list.sort((a, b) => (a.rank ?? 999) - (b.rank ?? 999));
});

// 内部状态
const selectedRows = ref<any[]>([]);

// 监听弹窗打开，如果需要默认全选
watch(
  () => visible,
  val => {
    if (val && props.defaultSelectAll && tableRef.value) {
      // 下一帧执行以确保 DOM 渲染完成
      setTimeout(() => {
        tableRef.value?.toggleAllSelection();
      }, 0);
    }
    if (!val) {
      // 关闭时清空选中
      selectedRows.value = [];
      // 清空表格内部的选择状态，避免下次打开时残留
      tableRef.value?.clearSelection();
    }
  }
);

// 处理表格勾选变化
const handleSelectionChange = (selection: any[]) => {
  selectedRows.value = selection;
  emit("selection-change", selection);
};

// 处理底部按钮点击
const handleDialogButtonClick = (btn: globalThis.ButtonProp) => {
  emit("dialog-button-click", btn.eventName, btn, selectedRows.value);
};

// 暴露方法给父组件（例如手动刷新表格或清空选中）
const clearSelection = () => {
  tableRef.value?.clearSelection();
};
const toggleRowSelection = (row: any, selected?: boolean) => {
  tableRef.value?.toggleRowSelection(row, selected);
};
const checkPermission = (buttonEventName?: string) => {
  if (!buttonEventName) return true;
  return dialogButtonList.value.find(item => item.eventName === buttonEventName) !== undefined;
};

defineExpose({
  clearSelection,
  toggleRowSelection,
  tableRef,
});
</script>

<template>
  <el-dialog v-model="visible" :title="title" :close-on-click-modal="false" :lock-scroll="false" width="80%">
    <!-- 1. 顶部筛选区域 (Slot) -->
    <div class="dialog-filter-area">
      <slot name="filter" :refresh="() => emit('filter-refresh')" :selected-rows="selectedRows">
        <!-- 默认空内容，由父组件填充 -->
      </slot>
    </div>

    <!-- 2. 中部表格区域 -->
    <div class="dialog-table-area">
      <el-table
        ref="tableRef"
        :data="tableData"
        :row-key="rowKey"
        border
        stripe
        style="width: 100%"
        :loading="loading"
        max-height="50vh"
        @selection-change="handleSelectionChange"
      >
        <!-- 勾选列 -->
        <el-table-column type="selection" width="55" v-if="selectable" />

        <!-- 父组件自定义列 -->
        <slot name="table-columns"></slot>

        <!-- 如果没有权限按钮且父组件也没传操作列，可以留空或显示提示 -->
      </el-table>

      <!-- 提示信息：当无数据时 -->
      <el-empty v-if="!loading && tableData.length === 0" description="暂无数据" />
    </div>

    <!-- 3. 底部区域 (修改部分) -->
    <template #footer>
      <div class="dialog-footer-container">
        <!-- 左侧：统计信息 -->
        <div class="footer-summary" v-if="showSummary">
          <span class="total-count">{{ summaryText }} {{ tableData.length }} 条</span>
          <span v-if="selectedRows.length > 0" class="selected-count">(已选 {{ selectedRows.length }} 条)</span>
        </div>

        <!-- 右侧：操作按钮 -->
        <div class="footer-actions">
          <slot name="attachment" :selected-rows="selectedRows" :checkPermission="checkPermission">
            <!-- 默认内容为空，不影响原有布局 -->
          </slot>
          <el-button
            v-for="btn in dialogButtonList"
            :key="btn.buttonName"
            :type="btn.colorType || 'primary'"
            :disabled="selectedRows.length === 0 && !['cancel'].includes(btn.eventName)"
            @click="handleDialogButtonClick(btn)"
          >
            {{ $t("_button." + btn.eventName) || btn.text }}
          </el-button>

          <el-button @click="visible = false">
            {{ $t("_button.cancel") || "取消" }}
          </el-button>
        </div>
      </div>
    </template>
  </el-dialog>
</template>

<style scoped>
.footer-actions {
  display: flex;
  gap: 12px;
  align-items: center;
}

.dialog-footer-container {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
}

.footer-summary {
  display: flex;
  gap: 8px;
  align-items: center;
}

.total-count {
  font-size: 14px;
  font-weight: 500;
  color: var(--el-text-color-primary);
}

.selected-count {
  font-size: 13px;
  font-weight: 500;
  color: var(--el-color-primary);
}

.dialog-filter-area {
  padding: 12px 16px;
  margin-bottom: 16px;
  background-color: var(--el-fill-color-lighter);
  border: 1px solid var(--el-border-color-lighter);
  border-radius: 6px;
}

.dialog-table-area {
  min-height: 200px;
  max-height: 60vh;
  overflow-y: auto;
}

.dialog-footer {
  display: flex;
  gap: 12px;
  justify-content: flex-end;
}

:deep(.el-dialog) {
  overflow: hidden;
  border-radius: 8px;
}

:deep(.el-dialog__body) {
  overflow-y: auto;
  scrollbar-gutter: stable;
}

:deep(.el-dialog__header) {
  padding: 16px 20px;
  margin-right: 0;
  background-color: var(--el-fill-color-light);
  border-bottom: 1px solid var(--el-border-color-lighter);
}

:deep(.el-dialog__title) {
  font-size: 16px;
  font-weight: 600;
  color: var(--el-text-color-primary);
}

:deep(.el-dialog__headerbtn) {
  top: 16px;
}

:deep(.el-table) {
  font-size: 13px;
}

:deep(.el-table th.el-table__cell) {
  font-weight: 600;
  background-color: var(--el-fill-color-light);
}
</style>
