<template>
  <el-row :gutter="20">
    <el-col :class="{'leftcontent': true, 'collapsed': isLeftContentCollapsed}" :span="isLeftContentCollapsed ? 0 : 4" :xs="24">
      <ContentWrap class="h-1/1">
        <DeptTree @node-click="handleDeptNodeClick" />
      </ContentWrap>
    </el-col>
    <el-col class="rightcontent" :span="isLeftContentCollapsed ? 24 : 20" :xs="24" style="position: relative;height: 100vh;">
      <div
        class="toggle-button"
        :style="{ left: isLeftContentCollapsed ? '0px' : '-13px' }"
        @click="toggleLeftContent"
        @mouseover="handleMouseOver"
        @mouseout="handleMouseOut"
        :title="hoverText"
      >
        <span style="font-size: 5px;" :class="{'triangle': true, 'rotated': isLeftContentCollapsed}"></span>
      </div>
      <ContentWrap>
        <!-- 搜索工作栏 -->
        <el-form
          class="-mb-15px"
          :model="queryParams"
          ref="queryFormRef"
          :inline="true"
          label-width="68px"
        >
          <el-form-item :label="t('bomList.name')" prop="name">
            <el-input
              v-model="queryParams.name"
              :placeholder="t('bomList.nHolder')"
              clearable
              @keyup.enter="handleQuery"
              class="!w-240px"
            />
          </el-form-item>
          <el-form-item :label="t('bomList.status')" prop="result">
            <el-select
              v-model="queryParams.result"
              :placeholder="t('bomList.status')"
              clearable
              class="!w-240px"
            >
              <el-option
                v-for="dict in resultOptions"
                :key="dict.value"
                :label="dict.label"
                :value="dict.value"
              />
            </el-select>
          </el-form-item>
          <el-form-item :label="t('common.createTime')" prop="createTime" label-width="100px">
            <el-date-picker
              v-model="queryParams.createTime"
              value-format="YYYY-MM-DD HH:mm:ss"
              type="daterange"
              :start-placeholder="t('operationFill.start')"
              :end-placeholder="t('operationFill.end')"
              :default-time="[new Date('1 00:00:00'), new Date('1 23:59:59')]"
              class="!w-220px"
            />
          </el-form-item>
          <el-form-item>
            <el-button @click="handleQuery"><Icon icon="ep:search" class="mr-5px" />
              {{ t('operationFill.search') }}</el-button>
            <el-button @click="resetQuery"><Icon icon="ep:refresh" class="mr-5px" /> {{ t('operationFill.reset') }}</el-button>
            <el-button
              type="primary"
              plain
              @click="openForm('create')"
              v-hasPermi="['pms:iot-main-work-order:create']"
            >
              <Icon icon="ep:plus" class="mr-5px" />  {{ t('operationFill.add') }}
            </el-button>
            <el-button
              type="success"
              plain
              @click="handleExport"
              :loading="exportLoading"
              v-hasPermi="['pms:iot-main-work-order:export']"
            >
              <Icon icon="ep:download" class="mr-5px" /> 导出
            </el-button>
          </el-form-item>
        </el-form>
      </ContentWrap>

      <!-- 列表 -->
      <ContentWrap ref="tableContainerRef" class="table-wrap">
        <el-table v-loading="loading" :data="list" :stripe="true" style="width: 100%" ref="tableRef">
          <el-table-column :label="t('iotDevice.serial')" align="center" :width="columnWidths.serial">
            <template #default="scope">
              {{ scope.$index + 1 }}
            </template>
          </el-table-column>
          <el-table-column :label="t('bomList.name')" align="center" prop="name" :width="columnWidths.name"/>
          <el-table-column :label="t('iotDevice.dept')" align="center" prop="deptName" :width="columnWidths.deptName"/>
          <el-table-column :label="t('bomList.status')" align="center" prop="result" :width="columnWidths.result">
            <template #default="scope">
              <dict-tag :type="DICT_TYPE.PMS_MAIN_WORK_ORDER_RESULT" :value="scope.row.result" />
            </template>
          </el-table-column>
          <el-table-column :label="t('bomList.serviceDue')" align="center" :width="columnWidths.serviceDue">
            <template #default="scope">
          <span :class="getDistanceClass(scope.row.mainDistance)">
            {{ scope.row.mainDistance }}
          </span>
            </template>
          </el-table-column>
          <el-table-column :label="t('bomList.type')" align="center" prop="type" :width="columnWidths.type">
            <template #default="scope">
              <dict-tag :type="DICT_TYPE.PMS_MAIN_WORK_ORDER_TYPE" :value="scope.row.type" />
            </template>
          </el-table-column>
          <el-table-column :label="t('iotMaintain.PersonInCharge')" align="center"
                           prop="responsiblePersonName" :width="columnWidths.responsiblePersonName"/>
          <el-table-column
            :label="t('dict.createTime')"
            align="center"
            prop="createTime"
            :formatter="dateFormatter"
            :width="columnWidths.createTime"
          />
          <el-table-column
            :label="t('dict.fillTime')"
            align="center"
            prop="updateTime"
            :width="columnWidths.updateTime"
          >
            <template #default="scope">
          <span v-if="scope.row.result == 2">
            {{ formatCellDate(scope.row.updateTime) }}
          </span>
              <span v-else></span>
            </template>
          </el-table-column>
          <el-table-column :label="t('iotMaintain.operation')" align="center" :width="columnWidths.operation" fixed="right">
            <template #default="scope">
              <el-button
                v-if="isNegativeMainDistance(scope.row.mainDistance)"
                link
                :type="getDelayReasonButtonType(scope.row.delayReason)"
                @click="openDelayReasonDialog(scope.row)"
                v-hasPermi="['pms:iot-main-work-order:update']"
              >
                {{ t('mainPlan.delayed') || '延时' }}
              </el-button>
              <el-button
                link
                type="primary"
                @click="openForm('update', scope.row.id)"
                v-hasPermi="['pms:iot-main-work-order:update']"
                v-if="scope.row.result === 1"
              >
                {{ t('operationFill.fill') }}
              </el-button>
              <el-button
                link
                type="primary"
                @click="detail(scope.row.id)"
                v-hasPermi="['pms:iot-main-work-order:query']"
              >
                {{ t('operationFill.view')  }}
              </el-button>
            </template>
          </el-table-column>
        </el-table>
        <!-- 分页 -->
        <Pagination
          :total="total"
          v-model:page="queryParams.pageNo"
          v-model:limit="queryParams.pageSize"
          @pagination="getList"
        />
      </ContentWrap>
    </el-col>
  </el-row>
  <!-- 表单弹窗：添加/修改 -->
  <IotMainWorkOrderForm ref="formRef" @success="getList" />

  <!-- 延保原因弹窗 -->
  <el-dialog
    v-model="delayReasonDialogVisible"
    :title="t('workOrderMaterial.delayReason') || '延时原因'"
    width="500px"
    :close-on-click-modal="false"
  >
    <el-form :model="delayReasonForm" label-width="0px" :rules="delayReasonRules"
             ref="delayReasonFormRef">
      <el-form-item label=" " prop="delayReason" class="required-item" label-width="16px">
        <el-input
          v-model="delayReasonForm.delayReason"
          type="textarea"
          :rows="4"
          :placeholder="t('workOrderMaterial.inputDelayReason') || '请输入延时原因'"
          maxlength="500"
          show-word-limit
        />
      </el-form-item>
    </el-form>
    <template #footer>
      <el-button @click="delayReasonDialogVisible = false">
        {{ t('common.cancel') || '取消' }}
      </el-button>
      <el-button type="primary" @click="saveDelayReason" :loading="saveDelayReasonLoading">
        {{ t('common.save') || '保存' }}
      </el-button>
    </template>
  </el-dialog>

</template>

<script setup lang="ts">
import { dateFormatter } from '@/utils/formatTime'
import download from '@/utils/download'
import { IotMainWorkOrderApi, IotMainWorkOrderVO } from '@/api/pms/iotmainworkorder'
import IotMainWorkOrderForm from './IotMainWorkOrderForm.vue'
import {DICT_TYPE, getStrDictOptions} from "@/utils/dict";
import DeptTree from "@/views/system/user/DeptTree.vue";
const { push } = useRouter() // 路由跳转

/** 保养工单 列表 */
defineOptions({ name: 'IotMainWorkOrder' })

// 表单引用
const delayReasonFormRef = ref<InstanceType<typeof ElForm>>()

const message = useMessage() // 消息弹窗
const { t } = useI18n() // 国际化
const tableRef = ref() // 表格引用
const isLeftContentCollapsed = ref(false);
// 表格容器引用 用于获取容器宽度
const tableContainerRef = ref()
const loading = ref(true) // 列表的加载中
const list = ref<IotMainWorkOrderVO[]>([]) // 列表的数据
const total = ref(0) // 列表的总页数
const queryParams = reactive({
  pageNo: 1,
  pageSize: 10,
  planId: undefined,
  planSerialNumber: undefined,
  deptId: undefined,
  orderNumber: undefined,
  name: undefined,
  type: undefined,
  responsiblePerson: undefined,
  responsiblePersonName: undefined,
  cost: undefined,
  result: undefined,
  otherCost: undefined,
  laborCost: undefined,
  outsourcingFlag: undefined,
  actualStartTime: [],
  actualEndTime: [],
  remark: undefined,
  status: undefined,
  processInstanceId: undefined,
  auditStatus: undefined,
  createTime: [],
})
const queryFormRef = ref() // 搜索的表单
const exportLoading = ref(false) // 导出的加载中
const hoverText = ref('');

// 定义表单验证规则
const delayReasonRules = {
  delayReason: [
    { required: true, message: t('workOrderMaterial.inputDelayReason') || '请输入延时原因', trigger: 'blur' }
  ]
}

// 列宽度配置
const columnWidths = ref({
  serial: '80px',
  name: '200px',
  deptName: '150px',
  result: '120px',
  serviceDue: '150px',
  type: '120px',
  responsiblePersonName: '150px',
  createTime: '180px',
  updateTime: '180px',
  operation: '150px'
})

// 计算文本宽度
const getTextWidth = (text: string, fontSize = 14) => {
  const span = document.createElement('span');
  span.style.visibility = 'hidden';
  span.style.position = 'absolute';
  span.style.whiteSpace = 'nowrap';
  span.style.fontSize = `${fontSize}px`;
  span.style.fontFamily = 'inherit';
  span.innerText = text;

  document.body.appendChild(span);
  const width = span.offsetWidth;
  document.body.removeChild(span);

  return width;
};

/** 延保原因相关状态 */
const delayReasonDialogVisible = ref(false)
const saveDelayReasonLoading = ref(false)
const delayReasonForm = reactive({
  id: undefined as number | undefined,
  delayReason: ''
})

/** 判断mainDistance是否为负值 */
const isNegativeMainDistance = (mainDistance: string | null): boolean => {
  if (!mainDistance) return false

  // 使用正则提取数字部分（包括负号、小数点和科学计数法）
  const numericPart = mainDistance.match(/[-+]?\d*\.?\d+(?:[eE][-+]?\d+)?/)?.[0]

  if (numericPart) {
    const num = parseFloat(numericPart)
    return num < 0
  }

  return false
}

/** 打开延保原因弹窗 */
const openDelayReasonDialog = (row: IotMainWorkOrderVO) => {
  delayReasonForm.id = row.id
  delayReasonForm.delayReason = row.delayReason || ''
  delayReasonDialogVisible.value = true
}

/** 保存延保原因 */
const saveDelayReason = async () => {
  // 表单验证
  if (!delayReasonFormRef.value) return
  const valid = await delayReasonFormRef.value.validate()
  if (!valid) return

  if (!delayReasonForm.id) {
    message.error('ID不能为空')
    return
  }

  try {
    saveDelayReasonLoading.value = true
    // 调用更新接口，只传递id和delayReason字段
    await IotMainWorkOrderApi.updateIotMainWorkOrder({
      id: delayReasonForm.id,
      delayReason: delayReasonForm.delayReason
    })

    message.success(t('common.success') || '保存成功')
    delayReasonDialogVisible.value = false

    // 刷新列表数据
    await getList()
  } catch (error) {
    console.error('保存延保原因失败:', error)
    message.error(t('sys.api.operationFailed') || '保存失败')
  } finally {
    saveDelayReasonLoading.value = false
  }
}

/** 根据delayReason是否有值返回按钮类型 */
const getDelayReasonButtonType = (delayReason: string | null | undefined): string => {
  // 如果delayReason有值（不为null、undefined且不是空字符串），返回success，否则返回warning
  return delayReason ? 'success' : 'warning'
}

/** 处理部门被点击 */
const handleDeptNodeClick = async (row) => {
  queryParams.deptId = row.id
  await getList()
}

// 计算列宽度
const calculateColumnWidths = () => {
  const MIN_WIDTH = 80; // 最小列宽
  const PADDING = 25; // 列内边距
  const FLEXIBLE_COLUMN = 'name'; // 可伸缩列

  // 确保表格容器存在
  if (!tableContainerRef.value?.$el) return;

  const container = tableContainerRef.value.$el;
  const containerWidth = container.clientWidth;

  // 1. 计算所有列的最小宽度
  const minWidths: Record<string, number> = {};
  let totalMinWidth = 0;

  // 计算列最小宽度的函数
  const calculateColumnMinWidth = (key: string, label: string, getValue: Function) => {
    const headerWidth = getTextWidth(label) * 1.2;
    let contentMaxWidth = 0;

    // 计算内容最大宽度
    list.value.forEach((row, index) => {
      const text = String(getValue ? getValue(row, index) : (row[key] || ''));
      const textWidth = getTextWidth(text);
      if (textWidth > contentMaxWidth) contentMaxWidth = textWidth;
    });

    const minWidth = Math.max(headerWidth, contentMaxWidth, MIN_WIDTH) + PADDING;
    minWidths[key] = minWidth;
    totalMinWidth += minWidth;
    return minWidth;
  };

  // 计算各列最小宽度
  calculateColumnMinWidth('serial', t('iotDevice.serial'), (row: any, index: number) => `${index + 1}`);
  const nameMinWidth = calculateColumnMinWidth('name', t('bomList.name'), (row: any) => row.name);
  calculateColumnMinWidth('deptName', t('iotDevice.dept'), (row: any) => row.deptName);
  calculateColumnMinWidth('result', t('bomList.status'), (row: any) => {
    const dict = getStrDictOptions(DICT_TYPE.PMS_MAIN_WORK_ORDER_RESULT)
      .find(d => d.value === row.result);
    return dict ? dict.label : '';
  });
  calculateColumnMinWidth('serviceDue', t('bomList.serviceDue'), (row: any) => row.mainDistance || '');
  calculateColumnMinWidth('type', t('bomList.type'), (row: any) => {
    const dict = getStrDictOptions(DICT_TYPE.PMS_MAIN_WORK_ORDER_TYPE)
      .find(d => d.value === row.type);
    return dict ? dict.label : '';
  });
  calculateColumnMinWidth('responsiblePersonName', t('iotMaintain.PersonInCharge'), (row: any) => row.responsiblePersonName);
  calculateColumnMinWidth('createTime', t('dict.createTime'), (row: any) => dateFormatter(null, null, row.createTime));
  calculateColumnMinWidth('updateTime', t('dict.fillTime'), (row: any) => row.result == 2 ? formatCellDate(row.updateTime) : '');

  // 操作列固定宽度
  minWidths.operation = 160;
  totalMinWidth += 160;

  // 2. 计算可伸缩列最终宽度
  const newWidths: Record<string, string> = {};
  const availableWidth = containerWidth - 17; // 减去滚动条宽度

  // 应用最小宽度到所有列
  Object.keys(minWidths).forEach(key => {
    newWidths[key] = `${minWidths[key]}px`;
  });

  // 计算可伸缩列需要的宽度
  if (totalMinWidth < availableWidth) {
    // 有剩余空间：分配给可伸缩列
    newWidths[FLEXIBLE_COLUMN] = `${minWidths[FLEXIBLE_COLUMN] + (availableWidth - totalMinWidth)}px`;
  } else {
    // 空间不足：确保可伸缩列至少显示内容
    newWidths[FLEXIBLE_COLUMN] = `${nameMinWidth}px`;
  }

  // 3. 更新列宽配置
  columnWidths.value = newWidths;

  // 4. 触发表格重新布局
  nextTick(() => {
    tableRef.value?.doLayout();
  });
};

/** 查询列表 */
const getList = async () => {
  loading.value = true
  try {
    const data = await IotMainWorkOrderApi.sortedMainWorkOrderPage(queryParams)
    list.value = data.list
    total.value = data.total

    // 数据加载后计算列宽
    nextTick(() => {
      calculateColumnWidths()
      window.dispatchEvent(new Event('resize'))
    })
  } finally {
    loading.value = false
  }
}

// 日期格式化辅助函数
const formatCellDate = (dateString: string | null) => {
  if (!dateString) return '';
  return dateFormatter(null, null, dateString);
}

/** 搜索按钮操作 */
const handleQuery = () => {
  queryParams.pageNo = 1
  getList()
}

/** 重置按钮操作 */
const resetQuery = () => {
  queryFormRef.value.resetFields()
  handleQuery()
}

// 保养状态 下拉列表 添加数据字典外的选项
const resultOptions = computed(() => [
  {
    label: t('operationFill.all'),
    value: '0' // 空值会触发 clearable 效果
  },
  {
    label: t('mainPlan.delayed'),
    value: '3' // 空值会触发 clearable 效果
  },
  ...getStrDictOptions(DICT_TYPE.PMS_MAIN_WORK_ORDER_RESULT)
])

const getDistanceClass = (distance: number | string | null) => {
  if (distance === null || distance === undefined) return '';

  // 如果是数字类型，直接处理
  if (typeof distance === 'number') {
    return distance < 0 ? 'negative-distance' :
      distance > 0 ? 'positive-distance' : '';
  }

  // 如果是字符串，提取数字部分
  if (typeof distance === 'string') {
    // 使用正则提取数字部分（包括负号、小数点和科学计数法）
    const numericPart = distance.match(/[-+]?\d*\.?\d+(?:[eE][-+]?\d+)?/)?.[0];

    // 如果提取到数字部分，转换为数值
    if (numericPart) {
      const num = parseFloat(numericPart);
      return num < 0 ? 'negative-distance' :
        num > 0 ? 'positive-distance' : '';
    }
  }

  return '';
};

const toggleLeftContent = () => {
  isLeftContentCollapsed.value = !isLeftContentCollapsed.value;
};

const handleMouseOver = () => {
  hoverText.value = isLeftContentCollapsed.value ? '展开' : '收起';
};

const handleMouseOut = () => {
  hoverText.value = '';
};

/** 添加/修改操作 */
const formRef = ref()
const openForm = (type: string, id?: number) => {
  // 修改
  if (typeof id === 'number') {
    push({ name: 'IotMainWorkOrderOptimize', params: {id } })
    return
  } else {
    push({ name: 'IotMainWorkOrderAdd', params:{} })
  }
}

/** 删除按钮操作 */
const handleDelete = async (id: number) => {
  try {
    // 删除的二次确认
    await message.delConfirm()
    // 发起删除
    await IotMainWorkOrderApi.deleteIotMainWorkOrder(id)
    message.success(t('common.delSuccess'))
    // 刷新列表
    await getList()
  } catch {}
}

const detail = (id?: number) => {
  push({ name: 'IotMainWorkOrderDetail', params:{id} })
}

/** 导出按钮操作 */
const handleExport = async () => {
  try {
    // 导出的二次确认
    await message.exportConfirm()
    // 发起导出
    exportLoading.value = true
    const data = await IotMainWorkOrderApi.exportIotMainWorkOrder(queryParams)
    download.excel(data, '保养工单.xls')
  } catch {
  } finally {
    exportLoading.value = false
  }
}

// 声明 ResizeObserver 实例
let resizeObserver: ResizeObserver | null = null;

/** 初始化 **/
onMounted(() => {
  getList()
  window.addEventListener('resize', calculateColumnWidths);
  // 创建 ResizeObserver 监听表格容器尺寸变化
  if (tableContainerRef.value?.$el) {
    resizeObserver = new ResizeObserver(() => {
      // 使用防抖避免频繁触发
      clearTimeout(window.resizeTimer);
      window.resizeTimer = setTimeout(() => {
        calculateColumnWidths();
      }, 100);
    });
    resizeObserver.observe(tableContainerRef.value.$el);
  }
})

onUnmounted(() => {
  window.removeEventListener('resize', calculateColumnWidths);

  // 清除 ResizeObserver
  if (resizeObserver && tableContainerRef.value?.$el) {
    resizeObserver.unobserve(tableContainerRef.value.$el);
    resizeObserver = null;
  }

  // 清除定时器
  if (window.resizeTimer) {
    clearTimeout(window.resizeTimer);
  }
})

// 监听列表数据变化重新计算列宽
watch(list, () => {
  nextTick(calculateColumnWidths)
}, { deep: true })

// 监听左侧菜单状态变化（展开/收起）
watch(isLeftContentCollapsed, () => {
  // 添加延迟以确保 DOM 更新完成
  setTimeout(calculateColumnWidths, 50);
})

</script>
<style scoped>

.leftcontent {
  transition: width 0.3s ease;
  position: relative;
}

.leftcontent.collapsed {
  width: 0;
  overflow: hidden;
}

/* 正数样式 - 淡绿色 */
.positive-distance {
  color: #67c23a;  /* element-plus 成功色 */
  background-color: rgba(103, 194, 58, 0.1); /* 10% 透明度的淡绿色背景 */
  padding: 2px 8px;
  border-radius: 4px;
  display: inline-block;
}

/* 负数样式 - 淡红色 */
.negative-distance {
  color: #f56c6c;  /* element-plus 危险色 */
  background-color: rgba(245, 108, 108, 0.1); /* 10% 透明度的淡红色背景 */
  padding: 2px 8px;
  border-radius: 4px;
  display: inline-block;
}

.table-wrap {
  overflow-x: auto; /* 允许水平滚动 */
}

/* 确保所有内容不换行 */
:deep(.el-table) {
  min-width: 100% !important;
  width: auto !important;
}

/* 表头和单元格内容不换行 */
:deep(.el-table__header .el-table__cell .cell),
:deep(.el-table__body .el-table__cell .cell) {
  white-space: nowrap !important;
  overflow: visible !important;
  text-overflow: clip !important;
}

/* 防止表头内容换行 */
:deep(.el-table__header-wrapper) .el-table__cell > .cell {
  white-space: nowrap;
}

/* 确保表格行不换行 */
:deep(.el-table__row) {
  white-space: nowrap;
}

/* 表头特别处理 */
:deep(.el-table__header) {
  .cell {
    display: inline-block;
    white-space: nowrap;
    width: auto !important;
  }
}

/* 表格使用100%宽度 */
:deep(.el-table__inner-wrapper) {
  width: 100% !important;
}

.toggle-button {
  position: absolute;
  top: 44%;
  transform: translate(-65%,-50%);
  width: 12px;
  height: 40px;
  background-color: #f0f0f0;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  z-index: 1;
  clip-path: polygon(0 0, 100% 18%, 100% 85%, 0 100%);
  border-radius: 8px;
}

/* 添加鼠标悬停样式 */
.toggle-button:hover {
  background-color: #afafaf;
}

.triangle {
  width: 0;
  height: 0;
  border-top: 4px solid transparent;
  border-bottom: 4px solid transparent;
  transition: transform 0.4s ease;
  border-right: 5px solid gray; /* 修改为右边框显示颜色 */
  border-left: none; /* 移除左边框 */
}

.triangle.rotated {
  transform: rotate(180deg);
}

/* 延时原因 必填星号样式 */
:deep(.required-item .el-form-item__label:before) {
  content: '*';
  color: #ff4d4f;
  margin-right: 2px;
}

/* 调整标签区域样式 */
:deep(.required-item .el-form-item__label) {
  padding-right: 0 !important;
}
</style>
