<template>
  <z-paging
    class="page"
    ref="paging"
    v-model="dataList"
    :loading-more-enabled="false"
    @query="queryList"
  >
    <!-- z-paging默认铺满全屏，此时页面所有view都应放在z-paging标签内，否则会被盖住 -->
    <!-- 需要固定在页面顶部的view请通过slot="top"插入，包括自定义的导航栏 -->
    <view class="list">
      <!-- 工单基础信息 -->
      <view class="item top">
        <view class="item-content flex-row align-center">
          <view class="item-title full-cell flex-row align-center">
            <span class="item-title-width"
              >{{ $t("operationRecordFilling.workOrderName") }}:</span
            >
            <span>{{ params.orderName }}</span>
          </view>
        </view>
        <view class="item-content flex-row align-center">
          <view class="item-title full-cell flex-row align-center">
            <span class="item-title-width"
              >{{ $t("operationRecordFilling.responsiblePerson") }}:</span
            >
            <span>{{ params.userName }}</span>
          </view>
        </view>
        <view class="item-content flex-row align-center">
          <view class="item-title full-cell flex-row align-center">
            <span class="item-title-width"
              >{{ $t("operation.createTime") }}:</span
            >
            <span>{{ params.createTime }}</span>
          </view>
        </view>
      </view>
      <!-- 填报列表 -->
      <view class="item" v-for="(item, index) in dataList" :key="index">
        <view class="item-module flex-row align-center justify-between">
          <view class="module-name">
            {{ item.deviceCode }}({{ item.deviceName }})
          </view>
          <view class="module-border"> </view>
        </view>
        <view class="item-content flex-row align-center justify-between bold">
          <view class="item-title flex-row align-center">
            <span>{{ $t("operationRecordFilling.belongToTeam") }}:</span>
            <span>{{ item.orgName }}</span>
          </view>
        </view>
        <view
          class="item-content flex-row align-center justify-between bold"
          v-for="sum in item.sumList"
        >
          <view class="item-title flex-row align-center word-break-all">
            <span>{{ sum.name }}:</span>
          </view>
          <view class="item-value flex-row align-center justify-end total">
            <uni-easyinput
              style="text-align: right"
              :inputBorder="false"
              :clearable="true"
              :styles="{ disableColor: '#fff' }"
              :value="`${sum.totalRunTime} ${
                sum.modelAttr ? (sum.modelAttr.includes('Time') ? 'h' : '') : ''
              }`"
              :disabled="true"
            ></uni-easyinput>
          </view>
        </view>
        <view
          class="item-content flex-col align-center justify-between"
          :class="{ 'bottom-bold': item.nonSumList.length > 0 }"
          v-for="nosum in item.nonSumList"
        >
          <!-- isCollection为1，提示：以下数值取自PLC，如有不符请修改 -->
          <uni-notice-bar
            :text="$t('operationRecordFilling.plcNotice')"
            v-if="nosum.isCollection == 1"
          />
          <view class="flex-row align-center justify-between item-content">
            <view class="item-title flex-row align-center">
              <span>{{ nosum.name }}:</span>
            </view>
            <!-- 判断填写项的属性 -->
            <!-- type为double时，输入框为数字类型 -->
            <view
              class="item-value flex-row align-center justify-end"
              v-if="nosum.type == 'double'"
            >
              <uni-easyinput
                style="text-align: right"
                :styles="{ disableColor: '#fff' }"
                :inputBorder="false"
                :clearable="true"
                :placeholder="$t('operation.PleaseFillIn')"
                :disabled="!isView"
                v-model="nosum.fillContent"
                :type="'digit'"
                @blur="
                  nosum.threshold > 0
                    ? checkThreshold(nosum)
                    : checkLessThreshold(nosum)
                "
                @change="handleFillContentChange(nosum, item)"
              ></uni-easyinput>
            </view>
            <!-- type为textarea时，输入框为文本类型 -->
            <view
              class="item-value flex-row align-center justify-end"
              v-else-if="nosum.type == 'textarea'"
            >
              <uni-easyinput
                style="text-align: right"
                :styles="{ disableColor: '#fff' }"
                :inputBorder="false"
                :clearable="true"
                :placeholder="$t('operation.PleaseFillIn')"
                :disabled="!isView"
                v-model="nosum.fillContent"
                :type="'textarea'"
                :autoHeight="true"
                :maxlength="-1"
              ></uni-easyinput>
            </view>
            <!-- type为enum时，使用下拉菜单 -->
            <view
              class="item-value textarea flex-row align-center justify-end"
              v-else-if="nosum.type == 'enum' && nosum.description !== null"
            >
              <uni-data-select
                :localdata="nosum.enumList"
                :styles="{ disableColor: '#fff' }"
                :clear="false"
                :disabled="!isView"
                :placeholder="$t('operation.PleaseSelect')"
                v-model="nosum.fillContent"
              ></uni-data-select>
            </view>
            <!-- 其他类型时，输入框为文本类型 -->
            <view class="item-value flex-row align-center justify-end" v-else>
              <uni-easyinput
                style="text-align: right"
                :styles="{ disableColor: '#fff' }"
                :inputBorder="false"
                :clearable="true"
                :placeholder="$t('operation.PleaseFillIn')"
                :disabled="!isView"
                v-model="nosum.fillContent"
                :type="'text'"
              ></uni-easyinput>
            </view>
          </view>
        </view>
      </view>
    </view>
    <!-- 如果需要使用页脚，请使用slot="bottom"slot节点不支持通过v-if或v-show动态显示/隐藏，若需要动态控制，可将v-if添加在其子节点上 -->
    <template #bottom>
      <button
        style="border-radius: 0"
        type="primary"
        @click="onSubmit()"
      >
        {{ $t("operation.save") }}
      </button>
    </template>
  </z-paging>
</template>

<script setup>
import { ref, reactive, getCurrentInstance, watch, onMounted } from "vue";
import { onReady, onLoad } from "@dcloudio/uni-app";
import dayjs from "dayjs";
import {
  getRecordFillingDetailGetPage,
  getRecordFillingDetailGetAttrs,
  recordFillingDetailInsertLog,
  getRecordFillingDetail,
  recordFillingUpOperationOrder,
} from "@/api/recordFilling";
import { getUserId, reloginByUserId } from "@/utils/auth.js";
import { useDataDictStore } from "@/store/modules/dataDict";
// 引用全局变量$t
const { appContext } = getCurrentInstance();
const t = appContext.config.globalProperties.$t;

// 获取字典项
const { getStrDictOptions, getIntDictOptions } = useDataDictStore();

// -------------------------------------
const isFromMsg = ref(false);
const params = ref({});
const isView = ref(false); // 是否编辑 -- view == 1为编辑状态

onMounted(() => {
  console.log("onMounted");
});

onReady(() => {
  console.log("onReady");
});

onLoad(async (option) => {
  console.log("onLoad", option);
  await reloginByUserId(option.reloginUserId);
  isFromMsg.value = !!option.reloginUserId;
  // 初始化params
  params.value = JSON.parse(option.param);
  // 处理createTime
  params.value.createTime = params.value.createTime
    ? dayjs(Number.parseInt(params.value.createTime)).format("YYYY-MM-DD")
    : "";
  // 请求工单详情
  if (params.value?.orderId) {
    const detail = (await getRecordFillingDetail(params.value.orderId)).data;
    console.log("🚀getRecordFillingDetail ~ detail:", detail);
    params.value = {
      ...params.value,
      ...detail,
      // 处理createTime
      createTime: detail.createTime
        ? dayjs(Number.parseInt(detail.createTime)).format("YYYY-MM-DD")
        : "",
      orderId: detail.id,
    };
  }

  console.log("🚀 ~ params.value:", params.value);
  // 处理是否可编辑 {0: '待填写', 1: '已完成', 2: '填写中', 3: '忽略'}
  isView.value = params.value?.orderStatus % 2 == 0;
  console.log("🚀 ~ isView.value:", isView.value);
});
const paging = ref(null);
// v-model绑定的这个变量不要在分页请求结束中自己赋值，直接使用即可
const dataList = ref([]);

// 监听dataList变化，初始化时计算一次总和
watch(
  dataList,
  (newVal) => {
    // calculateTotalRunTime();
  },
  { deep: true }
);

// 处理fillContent变化的方法
const handleFillContentChange = (nosum, deviceItem) => {
  console.log("🚀 ~ nosum, deviceItem:", nosum, deviceItem);
  // 处理增压机
  if (
    deviceItem.deviceName.includes("增压机") &&
    nosum.name === "当日运转时间"
  ) {
    calculateTotalRunTime("增压机", "当日运转时间"); // 计算当日运转时间总和
  }
  // 处理提纯撬
  if (deviceItem.deviceName.includes("提纯撬") && nosum.name === "当日注气量") {
    calculateTotalRunTime("提纯撬", "当日注气量"); // 计算当日注气量总和
  }
  // 处理注水泵
  if (deviceItem.deviceName.includes("注水泵") && nosum.name === "当日注水量") {
    calculateTotalRunTime("注水泵", "当日注水量"); // 计算当日注水量总和
  }
  // 处理箱式变电站
  if (
    deviceItem.deviceName.includes("箱式变电站") &&
    nosum.name === "当日用电量"
  ) {
    calculateTotalRunTime("箱式变电站", "当日用电量"); // 计算当日用电量总和
  }
};

/**
 * 计算所有deviceName中包含deviceNameToMatch的对象中对应的reportName的fillContent总和并更新到reportName的fillContent中
 * @param deviceNameToMatch {string} 设备名称包含的字符串
 * @param reportName {string} 填写项名称
 */
const calculateTotalRunTime = (deviceNameToMatch, reportName) => {
  console.log(
    "🚀calculateTotalRunTime ~ deviceNameToMatch, reportName:",
    deviceNameToMatch,
    12
  );
  // 查找isReport为1的对象
  const reportItem = dataList.value.find((item) => item.isReport === 1);
  console.log("🚀calculateTotalRunTime ~ reportItem:", reportItem);

  if (!reportItem) return;
  /**
   * @param deviceNameToMatch {string} 设备名称包含的字符串
   * @param deviceName {string} 设备名称
   * @param reportName {string} 填写项名称
   * 查找[生产日报]中对应的填写项
   * reportName -> deviceName:reportName
   * 当日运转时间 -> 增压机:当日运转时间
   * 当日注气量 -> 提纯撬:当日注气量
   * 当日注水量 -> 注水泵:当日注水量
   * 当日用电量 -> 箱式变电站:当日用电量
   */
  const targetItem = reportItem.nonSumList.find(
    (item) => item.name === reportName
  );

  if (!targetItem) return;

  // 计算所有deviceName中包含deviceNameToMatch的对象中对应的reportName的fillContent总和
  let total = null;
  dataList.value.forEach((item) => {
    if (item.deviceName.includes(deviceNameToMatch) && item.nonSumList) {
      item.nonSumList.forEach((nonSum) => {
        // 只累加数字类型的值
        if (
          nonSum.type === "double" &&
          nonSum.fillContent &&
          nonSum.name === reportName
        ) {
          console.log("🚀 ~ nonSum.fillContent:", nonSum.fillContent);
          console.log("🚀 ~ nonSum:", nonSum);
          const value = Number(nonSum.fillContent) || 0;
          total += value;
        }
      });
    }
  });
  console.log("🚀 ~ total:", total);
  if (total !== null) {
    // 更新目标值，保留两位小数
    targetItem.fillContent = toFixed(total);
    console.log("🚀 ~ targetItem.fillContent:", targetItem.fillContent);
  }
};

// @query所绑定的方法不要自己调用！！需要刷新列表数据时，只需要调用paging.value.reload()即可
const queryList = (pageNo, pageSize) => {
  const userId = uni.getStorageSync("userId");
  if (!userId) {
    paging.value.complete([]);
    return;
  }

  // 此处请求仅为演示，请替换为自己项目中的请求
  getRecordFillingDetailGetPage({
    // pageNo,
    // pageSize,
    ...params.value,
    deviceCategoryId: 1,
  })
    .then(async (res) => {
      const resList = [].concat(res.data);

      // 使用Promise.all等待所有异步请求完成
      await Promise.all(
        resList.map(async (item) => {
          try {
            const attrParams = {
              deviceCode: item.deviceCode,
              deviceName: item.deviceName,
              deptId: item.deptId,
              createTime: params.value.createTime,
              deviceCategoryId: item.deviceCategoryId,
              deviceId: item.deviceId,
              userId: params.value.userId,
              orderId: params.value.orderId,
            };
            // console.log(
            //   "getRecordFillingDetailGetAttrs- attrParams",
            //   attrParams
            // );
            const resAttrs = await getRecordFillingDetailGetAttrs({
              pageNo: 1,
              pageSize: 10,
              ...attrParams,
            });
            // console.log("resAttrs", resAttrs);
            if (resAttrs?.data) {
              attrParams.createTime = attrParams.createTime
                ? dayjs(attrParams.createTime).format("YYYY-MM-DD")
                : "";
              attrParams.id = attrParams.orderId;
              delete attrParams.orderId;
              delete attrParams.deviceName;
              resAttrs.data.map((rtem) => {
                // 将rtem中sumList和nonSumList两个数组中的
                // fillContent字段判断是否为null, 如果为null,则赋值为0 不为null则保留两位小数
                // 将attrParams合并到两个数组的每个对象中
                // 然后将sumList和nonSumList分别赋值给item的sumList和nonSumList

                if (rtem.sumList) {
                  rtem.sumList.map((sumItem) => {
                    if (
                      sumItem.fillContent == null ||
                      sumItem.fillContent == ""
                    ) {
                      // console.log("🚀 ~ rtem.sumList.map ~ sumItem:", sumItem);
                      // sumItem.fillContent = 0;
                    } else {
                      // 如果是double类型，保留两位小数
                      if (sumItem.type == "double") {
                        sumItem.fillContent = toFixed(sumItem.fillContent);
                      }
                    }
                    // 将sumItem的id赋值给modelId
                    sumItem.modelId = sumItem.id;

                    sumItem.pointName = sumItem.name;
                    // 合并attrParams到sumItem中
                    sumItem = Object.assign(sumItem, attrParams);
                  });
                }
                if (rtem.nonSumList) {
                  //
                  rtem.nonSumList.map((nonSumItem) => {
                    if (
                      nonSumItem.fillContent == null ||
                      nonSumItem.fillContent == ""
                    ) {
                      // console.log(
                      //   "🚀 ~ rtem.nonSumList.map ~ nonSumItem:",
                      //   nonSumItem
                      // );
                      // nonSumItem.fillContent = 0;
                    } else {
                      // 如果是double类型，保留两位小数
                      if (nonSumItem.type == "double") {
                        nonSumItem.fillContent = toFixed(
                          nonSumItem.fillContent
                        );
                      }
                    }
                    nonSumItem.pointName = nonSumItem.name;
                    // 将nonSumItem的id赋值给modelId
                    nonSumItem.modelId = nonSumItem.id;
                    // 合并attrParams到nonSumItem中
                    nonSumItem = Object.assign(nonSumItem, attrParams);
                    // 如果是enum类型，且description不为null,则根据description获取对应字典项数组，赋值给enumList
                    if (nonSumItem.type == "enum" && nonSumItem.description) {
                      console.log("🚀 ~ onSumItem.description:");
                      nonSumItem.enumList =
                        nonSumItem.name === "非生产原因"
                          ? getIntDictOptions(nonSumItem.description).map(
                              (dict) => {
                                return {
                                  ...dict,
                                  text: dict.label,
                                };
                              }
                            )
                          : getStrDictOptions(nonSumItem.description).map(
                              (dict) => {
                                return {
                                  ...dict,
                                  text: dict.label,
                                };
                              }
                            );
                      console.log(
                        "🚀 ~  nonSumItem.enumList:",
                        nonSumItem.enumList
                      );
                    }
                  });
                }
                item.sumList = rtem.sumList;

                item.nonSumList = rtem.nonSumList;
              });
              console.log("resAttrs-modelId", resAttrs);
            }
          } catch (error) {
            console.error("获取属性失败", error);
            // 可以选择设置默认值或标记错误状态
            item.sumList = [];
            item.nonSumList = [];
          }
        })
      );
      console.log("resList--", resList);
      // 将请求结果通过complete传给z-paging处理，同时也代表请求结束，这一行必须调用
      paging.value.complete(resList);
    })
    .catch((res) => {
      // 如果请求失败写paging.value.complete(false);
      // 注意，每次都需要在catch中写这句话很麻烦，z-paging提供了方案可以全局统一处理
      // 在底层的网络请求抛出异常时，写uni.$emit('z-paging-error-emit');即可
      paging.value.complete(false);
    });
};
// 判断是否小于阈值 (<0)
const checkLessThreshold = (item) => {
  if (item.fillContent < 0) {
    uni.showToast({
      title:
        item.name +
        t("operationRecordFilling.fillContentCannotLessThanThreshold") +
        "0",
      icon: "none",
    });
    item.fillContent = ""; // 清空输入
    return false; // 返回false表示校验失败
  }
};
// 判断是否大于阈值
const checkThreshold = (item) => {
  checkLessThreshold(item);
  // 如果threshold > 0，则判断fillContent是否大于threshold，如果大于则提示用户填写小于等于threshold的值
  if (item.fillContent > item.threshold) {
    uni.showToast({
      title:
        item.name +
        t("operationRecordFilling.fillContentCannotGreaterThanThreshold") +
        item.threshold,
      icon: "none",
    });
    item.fillContent = ""; // 清空输入
    return false; // 返回false表示校验失败
  }
};

// 保留两位小数
const toFixed = (num) => {
  if (num) {
    num = Number(num);
    num = num.toFixed(2);
  } else {
    num = 0.0;
  }
  return num;
};

const onSubmit = async () => {
  console.log("onSubmit", dataList.value);
  // 1. 校验所有必填项
  // 遍历dataList.value中nonSumList每个item（非生产日报 isReport!=1）的fillContent字段,
  // 如果为null或者为空，则提示用户填写，
  // 如果threshold > 0，则判断fillContent是否大于threshold，如果大于则提示用户填写小于等于threshold的值
  // 如果所有项全部填写，则调用填写记录接口

  for (const item of dataList.value) {
    const nonSumList = item.nonSumList;
    for (const nonSumItem of nonSumList) {
      if (
        (!item.isReport || item.isReport != 1) &&
        (nonSumItem.fillContent == null || nonSumItem.fillContent === "")
      ) {
        uni.showToast({
          title:
            t("operation.PleaseFillIn") +
            item.deviceCode +
            "(" +
            item.deviceName +
            ")" +
            t("operation.allItem"),
          icon: "none",
        });
        return; // 校验失败直接返回
      }
      if (nonSumItem.fillContent != "" && nonSumItem.fillContent != null) {
        console.log("🚀 ~ nonSumItem:", nonSumItem);
        console.log("🚀 ~ nonSumItem.fillContent:", nonSumItem.fillContent);
        // 先将值转换为字符串进行操作
        const fillContentStr = String(nonSumItem.fillContent);
        //  将字符串转换为数字
        const num = Number(fillContentStr);

        // 检查转换后的数字是否有效
        if (!isNaN(num)) {
          // 检查是否包含小数（使用字符串检查）
          if (fillContentStr.includes(".")) {
            // 保留两位小数（假设toFixed是你定义的保留两位小数的函数）
            nonSumItem.fillContent = toFixed(num);
          } else {
            // 转换为整数
            nonSumItem.fillContent = Math.floor(num);
          }
        }
      }
      // 如果threshold > 0，则判断fillContent是否大于threshold
      if (nonSumItem.threshold > 0) {
        if (nonSumItem.fillContent > nonSumItem.threshold) {
          uni.showToast({
            title:
              item.deviceCode +
              "(" +
              item.deviceName +
              ")" +
              nonSumItem.name +
              t(
                "operationRecordFilling.fillContentCannotGreaterThanThreshold"
              ) +
              nonSumItem.threshold,
            icon: "none",
            duration: 3000,
          });
          nonSumItem.fillContent = ""; // 清空输入
          return; // 校验失败直接返回
        }
      }
    }
  }
  // 定义新的dataList副本 用于提交数据，避免修改原数据
  const subDataList = JSON.parse(JSON.stringify(dataList.value));

  // 3. 处理副本：删除 enumList（仅修改副本，不影响原数据）
  for (const item of subDataList) {
    // 先判断 item.nonSumList 存在，避免空指针
    if (item.nonSumList && item.nonSumList.length) {
      for (const nonSumItem of item.nonSumList) {
        if (nonSumItem.enumList) {
          delete nonSumItem.enumList;
        }
      }
    }
  }
  console.log("提交用的副本数据：subDataList", subDataList);

  try {
    // 2. 收集所有保存请求（不在这里处理导航）
    const submitPromises = subDataList.map(async (item) => {
      const submitData = [].concat(item.sumList).concat(item.nonSumList);
      // 仅返回接口结果，不执行导航
      return await recordFillingDetailInsertLog(submitData);
    });

    // 3. 等待所有请求完成
    const results = await Promise.all(submitPromises);

    // 4. 所有请求完成后，统一判断结果
    const allSuccess = results.every((res) => res?.code === 0);
    if (allSuccess) {
      // 5. 调用更新工单状态接口
      const upRes = await recordFillingUpOperationOrder({
        id: params.value.orderId,
      });
      console.log("🚀 ~ upRes:", upRes)
      if (upRes?.code === 0) {
        console.log("工单状态更新成功");
        uni.showToast({
          title: t("operation.success"),
          duration: 1500,
          icon: "none",
        });
        setTimeout(() => {
          uni.navigateBack();
        }, 1500);
      } else {
        console.error("工单状态更新失败", upRes);
        uni.showToast({
          title: t("operation.fail"),
          icon: "none",
        });
      }
    } else {
      uni.showToast({
        title: t("operation.fail"),
        icon: "none",
      });
    }
  } catch (error) {
    console.error("保存失败", error);
    uni.showToast({
      title: t("operation.fail"),
      icon: "error",
    });
  }
};
</script>

<style lang="scss" scoped>
.page {
  padding: 0;
  box-sizing: border-box;
}

.top {
  padding: 10px;
}

.list {
  // margin-top: calc(10px);
  padding: 10px;
  height: calc(100%);
}

.item {
  width: 100%;
  // height: 204px;
  background: #ffffff;
  border-radius: 6px;
  margin-bottom: 10px;
  box-sizing: border-box;
  padding: 20px 15px;
}

.item-module {
  width: 100%;
  height: 16px;
  position: relative;
  font-weight: 600;
  font-size: 14px;
  color: #333333;
  margin-bottom: 10px;

  .module-border {
    position: absolute;
    left: -15px;
    width: 0px;
    height: 12px;
    border: 1px solid #004098;
  }
}

.item-content {
  position: relative;
  width: 100%;
  // height: calc(38px);
  box-sizing: border-box;
  font-weight: 500;
  font-size: 14px;
  color: #333333;
  line-height: 20px;
  border-bottom: 1px dashed #cacccf;

  &:last-child {
    border-bottom: none;
  }

  &.bold {
    font-weight: 600;
    // :deep(.uni-easyinput__content-input){
    // 	padding-right: 0 !important;
    // }
  }
  &.bottom-bold {
    border-bottom: 1px dashed #cacccf;
  }
}

.item-title {
  position: relative;
  min-height: 38px;
  width: 55%;

  &.total {
    :deep(.is-disabled) {
      color: #333333 !important;
    }
  }
  &.full-cell {
    width: 100%;
    min-width: max-content;
  }
}

.item-value {
  width: 45%;
  position: relative;
  &.textarea {
    width: 65%;
  }
}
.word-break-all {
  min-width: unset;
}
:deep(.uni-select) {
  border: none;
  text-align: right;
  padding-right: 0;
  .uniui-bottom:before {
    content: "\e6b5" !important;
    font-size: 16px !important;
  }
}
:deep(.uni-select--disabled) {
  color: #d5d5d5 !important;
  background-color: transparent;
  .uni-select__input-text {
    color: #d5d5d5 !important;
  }
}
:deep(.uni-select__selector) {
  text-align: left;
}
:deep(.uni-select__selector-item) {
  border-bottom: 1px dashed #cacccf;
  text-align: left;
}
:deep(.uni-easyinput__content-textarea) {
  min-height: inherit;
  margin: 10px;
}
</style>
