<template>
  <my-modal
    v-model:open="visible"
    title="导入卡格式"
    :width="600"
    @ok="submitHandle"
  >
    <qm-low-form
      :params="params"
      :fields="fields"
      :label-width="110"
      :rules="rules"
      ref="form"
    >
      <template #file>
        <ImportButton @fileChange="getFile" />
      </template>
      <template #subjectCode>
        <SelectSubject
          v-model="params.subjectCode"
          :exam-id="userStore.curExam?.id"
        ></SelectSubject>
      </template>
    </qm-low-form>
  </my-modal>
</template>
<script name="ImportCardDialog" lang="ts" setup>
import { ref, reactive, computed } from "vue";
import { importCard } from "@/ap/baseDataConfig";
import { useUserStore } from "@/store";
import SelectSubject from "@/components/SelectSubject/index.vue";
const userStore = useUserStore();
const form = ref();
const visible = defineModel();
const emit = defineEmits(["success"]);

const params = reactive({
  subjectCode: "",
  remark: "",
  file: null,
  paperCount: void 0,
  singlePage: false,
  dpi: 150,
});
const cardJson = ref(null);
const fields = computed(() => {
  return [
    {
      prop: "subjectCode",
      cell: "subjectCode",
      label: "科目题卡",
      colSpan: 24,
    },
    {
      prop: "remark",
      type: "textarea",
      label: "备注",
      colSpan: 24,
      attrs: {
        spellcheck: "false",
      },
    },
    { prop: "file", cell: "file", label: "选择卡格式", colSpan: 24 },
    {
      prop: "paperCount",
      type: "number",
      label: "张数",
      colSpan: 24,
      attrs: { min: 1 },
    },
    {
      prop: "singlePage",
      type: "radio",
      label: "单页题卡",
      colSpan: 24,
      attrs: {
        options: [
          { value: false, label: "否" },
          { value: true, label: "是" },
        ],
      },
    },
    params.file && isJson.value && cardJson.value && !cardJson.value.dpi
      ? {
          prop: "dpi",
          type: "radio",
          label: "DPI",
          colSpan: 24,
          attrs: {
            options: [
              { value: 150, label: "150" },
              { value: 200, label: "200" },
            ],
            disabled: cardJson.value?.dpi,
            onChange: () => {
              compareSize();
            },
          },
        }
      : null,
  ];
});
const isJson = ref(true);
const cardSizePass = ref(true);

const isJsonString = (str: string) => {
  try {
    const toObj = JSON.parse(str);
    if (toObj && typeof toObj === "object") {
      return true;
    }
  } catch {}
  return false;
};

const rules = {
  subjectCode: [{ required: true, message: "请选择科目" }],
  file: [
    { required: true, message: "请上传文件" },
    {
      validator: async () => {
        if (!isJson) {
          return Promise.reject("卡格式json文件内容异常，请检查");
        } else {
          if (cardJson.value && !cardSizePass.value) {
            return Promise.reject("卡格式图片dpi异常！");
          } else {
            return Promise.resolve();
          }
        }
      },
    },
  ],
  paperCount: [
    { required: true, message: "请输入张数" },
    {
      validator: async (rule: any, value: any) => {
        if (cardJson.value) {
          if (
            (params.singlePage && cardJson.value.pages.length != value) ||
            (!params.singlePage && cardJson.value.pages.length / 2 != value)
          ) {
            return Promise.reject("张数未校验通过，请检查！");
          } else {
            return Promise.resolve();
          }
        } else {
          return Promise.resolve();
        }
      },
    },
  ],
  dpi: [
    {
      validator: async () => {
        if (!isJson) {
          return Promise.reject("卡格式json文件内容异常，请检查");
        } else {
          if (cardJson.value && !cardSizePass.value) {
            return Promise.reject("卡格式图片dpi异常！");
          } else {
            return Promise.resolve();
          }
        }
      },
    },
  ],
};
let pageSizeStr = "";
let contentRecord: any = null;
let imgRecord: any = null;
const compareSize = () => {
  let target = contentRecord?.[pageSizeStr];
  let w = imgRecord?.width / params.dpi / 0.0394;
  let h = imgRecord?.height / params.dpi / 0.0394;
  if (Math.abs(w - target.width) > 10 || Math.abs(h - target.height) > 10) {
    cardSizePass.value = false;
  } else {
    cardSizePass.value = true;
  }
};
const validateCardSize = async (json: any) => {
  if (!json.pages.length) {
    cardSizePass.value = false;
    window.$message.error("卡格式文件里的pages为空");
    return;
  }
  window.electronApi?.getPageSizeIni((content: any) => {
    console.log(content);
    const img = new Image();
    img.onload = () => {
      pageSizeStr = json.pages[0].exchange["page_size"];
      contentRecord = content;
      imgRecord = img;
      compareSize();
    };
    img.onerror = function () {
      window.$message.error("卡格式json文件里的图片base64无效！");
    };
    img.src = "data:image/jpg;base64," + json.pages[0].exchange["page_image"];
  });
};
const getCardJsonContent = async (file: any) => {
  const reader = new FileReader();
  reader.onload = function (e) {
    try {
      const json = JSON.parse(e.target.result);
      console.log("json", json);
      cardJson.value = json;
      if (json.dpi) {
        params.dpi = Number(json.dpi);
      }
      validateCardSize(json);
    } catch (error) {
      console.error("Error parsing JSON:", error);
      isJson.value = false;
    }
  };

  reader.onerror = function (error) {
    console.error("File could not be read:", error);
  };

  reader.readAsText(file);
};
const getFile = (file: any) => {
  params.file = file;
  getCardJsonContent(file);
};
const submitHandle = () => {
  form.value.formRef.validate().then(() => {
    importCard({ examId: userStore.curExam?.id, ...params }).then(() => {
      emit("success");
      window.$message.success("导入成功");
      visible.value = false;
    });
  });
};
</script>
<style lang="less" scoped></style>
