<template>
  <div>
    <el-dialog
      v-model="visible"
      v-cloak
      width="90%"
      :close-on-press-escape="false"
      :close-on-click-modal="false"
      destroy-on-close
      :show-close="false"
      align-center
      append-to-body
    >
      <template #header>
        <div class="flex">
          <span>题目设置</span>
          <div class="flex justify-end items-center flex-1">
            <el-tooltip
              effect="dark"
              content="请添加并保存题目后再进行逻辑设置"
              placement="bottom"
            >
              <el-button
                type="warning"
                :disabled="!questions.length"
                @click="openLogicSetting"
                >逻辑设置</el-button
              >
            </el-tooltip>
            <el-button type="primary" @click="saveQuestions">保存</el-button>
            <el-button @click="visible = false">取消</el-button>
          </div>
        </div>
      </template>
      <div class="flex min-h-[50vh] p-4 space-x-4">
        <div
          class="bg-white border-gray-200 border-solid border rounded min-w-[160px] max-w-[220px] flex-1 p-4"
        >
          <draggable
            v-model="fixedQuestion"
            :group="{ name: 'questions', pull: 'clone', put: false }"
            item-key="type"
            :move="checkMove"
            :clone="cloneQuestion"
          >
            <template #item="{ element }">
              <div
                class="rounded mb-2 px-4 py-2 border border-gray-300 border-solid cursor-pointer hover:bg-gray-100"
              >
                {{ element.name }}
              </div>
            </template>
          </draggable>
          <!-- <div v-for="(item, index) in simpleTypes" :key="index"
          class="px-4 py-2 border border-gray-200 border-solid cursor-pointer hover:bg-gray-100">
            <span class="select-none">{{ item.name }}</span>
          </div> -->
        </div>
        <div
          class="max-h-[80vh] overflow-y-auto relative bg-white border-gray-200 border-solid border rounded shadow flex-[3] p-2 px-3"
        >
          <div
            v-if="!questions.length"
            class="absolute left-0 top-0 z-0 flex justify-center items-center w-full h-full overflow-hidden"
          >
            <img src="@/assets/survey-drag-tip.png" alt="" />
          </div>
          <draggable
            v-model="questions"
            class="h-full relative z-10"
            handle=".cursor-move"
            tag="transition-group"
            :group="{ name: 'questions' }"
            :component-data="{ name: 'fade' }"
            @change="onDragEnd"
          >
            <template #item="{ element, index }">
              <div
                class="p-2 border border-solid border-gray-300 rounded my-2"
                :class="{
                  'bg-yellow-50': element?.id == queryAttr?.id
                }"
              >
                <div class="flex justify-end items-center">
                  <div
                    class="flex items-center mr-4 text-gray-500 hover:text-blue-500 cursor-move"
                  >
                    <Rank class="w-5 h-5 mr-1" />
                    <span class="text-xs">移动</span>
                  </div>
                  <!-- <div
                    class="flex items-center text-gray-500 hover:text-blue-500 cursor-pointer"
                    @click="editQuestion(element, index)"
                  >
                    <Edit class="w-5 h-5 mr-1"></Edit>
                    <span class="text-xs">编辑</span>
                  </div> -->

                  <div
                    class="flex items-center mx-4 text-gray-500 hover:text-blue-500 cursor-pointer"
                    @click="copyQuestion(element, index)"
                  >
                    <CopyDocument class="w-5 h-5 mr-1" />
                    <span class="text-xs">复制</span>
                  </div>
                  <div
                    class="flex items-center text-gray-500 hover:text-red-500 cursor-pointer"
                    @click="removeQuestion(element, index)"
                  >
                    <Delete class="w-5 h-5 mx-1" />
                    <span class="text-xs">删除</span>
                  </div>
                </div>
                <!-- {{ element }} -->
                <div
                  class="cursor-pointer"
                  @click="editQuestion(element, index)"
                >
                  <SimpleQuestionItem
                    :info="element"
                    :id="element.id"
                    :edit="false"
                  />
                </div>
              </div>
            </template>
          </draggable>
        </div>
        <div
          v-show="queryAttr"
          class="bg-white border-gray-200 border-solid border rounded shadow flex-[2]"
        >
          <div class="p-4 flex items-center justify-between">
            <div>组件属性</div>
            <div
              class="text-red-400 text-xs flex items-center cursor-pointer hover:text-red-500 hover:bg-gray-50 p-1 rounded hover:underline"
              @click="queryAttr = undefined"
            >
              <Close class="w-4 h-4" />
              <span>关闭</span>
            </div>
          </div>
          <SimpleQuestionItem
            v-if="queryAttr"
            v-model:info="queryAttr"
            :id="queryAttr.id"
            :edit="true"
          />
        </div>
      </div>
    </el-dialog>
    <el-dialog v-model="logicSetting.visible" title="逻辑设置" append-to-body>
      <div>
        <el-button type="primary" @click="addLoginItem">+ 添加逻辑</el-button>
      </div>
      <!-- <div>
        {{ logicSetting.rules }}
      </div> -->
      <div class="py-4">
        <div
          v-for="(item, index) in logicSetting.rules"
          :key="index"
          class="flex items-center bg-gray-100 rounded relative p-4 m-2 mb-4"
        >
          <div class="flex-1 space-y-4">
            <div class="space-x-4">
              <span>如果</span>
              <el-select
                v-model="item.condition"
                clearable
                filterable
                @change="v => logicQuestionChange(v, item)"
              >
                <el-option
                  v-for="(opt, optIdx) in filterQuestions"
                  :key="optIdx"
                  :label="opt.title"
                  :value="opt.sn"
                />
              </el-select>
              <el-select v-model="item.type">
                <el-option label="选中" value="showHide" />
              </el-select>
              <el-select v-model="item.choose" clearable filterable @change="">
                <el-option
                  v-for="(opt, optIdx) in item?.choices"
                  :key="optIdx"
                  :label="opt.label"
                  :value="opt.attr"
                />
              </el-select>
            </div>
            <div class="space-x-4">
              <span>则</span>

              <el-select
                v-model="item.method"
                clearable
                filterable
                @change="v => logicMethodChange(v, item)"
              >
                <el-option label="跳转至指定题目" value="show" />
                <el-option label="隐藏指定题目内选项" value="hide" />
              </el-select>
              <el-select v-model="item.target" clearable filterable @change="">
                <el-option
                  v-for="(opt, optIdx) in item.targetQuestions"
                  :key="optIdx"
                  :label="opt.title"
                  :value="item.method == 'show' ? opt.sn : opt.attr"
                />
              </el-select>
            </div>
          </div>
          <div class="">
            <Delete
              class="w-5 h-5 cursor-pointer hover:text-red-500"
              @click="logicSetting.rules.splice(index, 1)"
            />
          </div>
        </div>
      </div>
      <template #footer>
        <el-button type="primary" @click="saveLogic">保存</el-button>
      </template>
    </el-dialog>
  </div>
</template>
<script setup>
import draggable from "vuedraggable";
import {
  simpleTypes,
  typeLabelByIndex as typeLabel
} from "@/enumerated/questionEnum";
import { request, randomString, parseJSON } from "@/utils";
import {
  ref,
  computed,
  defineProps,
  defineEmits,
  watch,
  nextTick,
  reactive
} from "vue";
import SimpleQuestionItem from "./SimpleQuestionItem.vue";
import { ElMessage } from "element-plus";
import {
  Edit,
  Rank,
  Delete,
  CopyDocument,
  Close
} from "@element-plus/icons-vue";

const props = defineProps({
  show: {
    type: Boolean,
    default: false
  },
  surveyId: {
    type: Number,
    default: undefined
  },
  submitLogic: {
    type: Function,
    default: undefined
  },
  submitQuestions: {
    type: Function,
    default: undefined
  },
  initQuestions: {
    type: Array,
    default: undefined
  },
  initRules: {
    type: Array,
    default: undefined
  }
});

const emits = defineEmits(["update:show"]);

const visible = computed({
  get() {
    return props.show;
  },
  set(n) {
    emits("update:show", n);
  }
});

const fixedQuestion = ref([...simpleTypes]);

const questions = ref([]);

const queryAttr = ref();

watch(
  () => visible.value,
  v => {
    if (v) {
      getQuestions();
    }
  }
);
const getQuestions = async () => {
  if (props.initQuestions) {
    questions.value = props.initQuestions;
    logicSetting.rules = props.initRules;
    return;
  }
  if (!props.surveyId) return;
  const { data } = await request.get(
    `/surveyService/mechanism/customSurvey/detail`,
    {
      params: {
        id: props.surveyId
      }
    }
  );
  if (data?.detail?.content?.content) {
    questions.value = parseJSON(data.detail.content.content);
  }
  if (data?.detail?.content?.logicCode) {
    logicSetting.rules = parseJSON(data.detail.content.logicCode);
  }
};

const checkMove = evt => {
  return evt.from !== evt.to;
};
const formatQuestionItem = raw => {
  const line = {
    ...raw,
    edit: false,
    title: raw.name || "",
    value: "",
    attr: randomString(7),
    sn: randomString(6),
    remark: "",
    combination: "",
    isRepeat: false,
    config: {
      desc: "",
      rule: "",
      type: "",
      regexRule: "",
      regexRuleName: ""
    },
    choices: [],
    children: []
  };
  switch (line.type) {
    case "radio":
      line.choices = [
        {
          label: "选项1",
          isInput: false,
          extra: "",
          inputPlaceholder: "",
          regexRule: "",
          regexRuleName: "",
          attr: randomString(6)
        },
        {
          label: "选项2",
          isInput: false,
          extra: "",
          inputPlaceholder: "",
          regexRule: "",
          regexRuleName: "",
          attr: randomString(6)
        }
      ];
      break;
    case "checkbox":
      line.choices = [
        {
          label: "选项1",
          mutuallyExclusive: false,
          isInput: false,
          extra: "",
          inputPlaceholder: "",
          regexRule: "",
          regexRuleName: "",
          attr: randomString(6)
        },
        {
          label: "选项2",
          mutuallyExclusive: false,
          isInput: false,
          extra: "",
          inputPlaceholder: "",
          regexRule: "",
          regexRuleName: "",
          attr: randomString(6)
        }
      ];
      line.isMultiple = true;
      break;
    case "scale":
      line.value = 0;

      line.min = 0;
      line.max = 100;
      line.choices = [
        {
          label: "开始"
        },
        {
          label: "结束"
        }
      ];
      break;
    case "rating_scale":
      line.min = 1;
      line.max = 5;
      line.choices = [
        {
          label: "不满意"
        },
        {
          label: "非常满意"
        }
      ];
      break;
    case "rating":
      line.choices = [
        {
          label: "选项1",
          score: 0
        },
        {
          label: "选项2",
          score: 0
        }
      ];
      line.isMultiple = false;
      break;
    case "date":
      break;

    case "disease":
    case "medicine":
      line.config.isInput = false;
      line.config.attr = "extra";
      line.recommend = [];
      line.searchList = [];
      line.cacheSearchList = [];
      line.systemTagIds = [];
      break;
    case "select":
      line.config.source = "graph";
      line.config.sourceTag = "";
      line.config.isMultiple = false;
      line.config.isAppendNull = false;

      break;
    case "matrix_checkbox":
      line.columns = [
        {
          label: "选项1",
          mutuallyExclusive: false,
          attr: randomString(6)
        },
        {
          label: "选项2",
          mutuallyExclusive: false,
          attr: randomString(6)
        }
      ];
      line.rows = [
        {
          label: "问题1",
          attr: randomString(6)
        },
        {
          label: "问题2",
          attr: randomString(6)
        }
      ];
      line.matrix = [];
      line.isMultiple = false;
      break;
    case "group":
      line.children = [];
      break;
    case "upload":
      line.config.fileType = "";
      line.config.fileSizeLimit = "";
      break;
  }
  return line;
};
const cloneQuestion = item => {
  console.log(item);
  return formatQuestionItem({ ...item, id: randomString() }); // 克隆时添加描述字段
};

const editQuestion = (item, index) => {
  console.log(item);
  queryAttr.value = item;
};
const copyQuestion = (item, index) => {
  const copyItem = {
    ...item,
    id: randomString(),
    sn: randomString(6),
    attr: randomString(7)
  };
  copyItem.choices.forEach(v => {
    v.attr = randomString(6);
  });
  copyItem.rows?.length &&
    copyItem.rows.forEach(v => {
      v.attr = randomString(6);
    });
  copyItem.columns?.length &&
    copyItem.columns.forEach(v => {
      v.attr = randomString(6);
    });
  questions.value.splice(index, 0, copyItem);
};
const removeQuestion = (item, index) => {
  questions.value.splice(index, 1);
  if (item.id == queryAttr.value.id) {
    queryAttr.value = undefined;
  }
};

const onDragEnd = event => {
  if (event.added) {
    queryAttr.value = questions.value[event.added.newIndex];
  }
};

const saveQuestions = async () => {
  // 在这里实现保存逻辑
  // console.log("保存成功:", selectedQuestion.value);
  console.log(questions.value);
  if (props.submitQuestions) {
    props.submitQuestions(questions.value);
    return;
  }
};

const logicSetting = reactive({
  visible: false,
  rules: []
});
const filterQuestions = computed(() =>
  questions.value.filter(item => ["radio", "checkbox"].includes(item.type))
);

const openLogicSetting = () => {
  logicSetting.visible = true;
};
const addLoginItem = () => {
  logicSetting.rules.push({
    type: "showHide",
    method: "show",
    condition: "",
    target: "",
    question: "",
    expression: "",
    choose: "",
    choices: [],
    targetQuestions: []
  });
};
const logicQuestionChange = (v, item) => {
  const chooseIdx = questions.value.findIndex(i => i.sn === item.condition);
  const chooseItem = filterQuestions.value[chooseIdx];
  console.log(chooseItem, item);
  item.choices = chooseItem?.choices || [];
  item.targetQuestions = questions.value.filter((v, k) => k > chooseIdx);
};

const logicMethodChange = (v, item) => {
  console.log(v);
  item.target = "";
  if (v == "hide") {
    const chooseIdx = filterQuestions.value.findIndex(
      i => i.sn === item.condition
    );
    item.targetQuestions = filterQuestions.value
      .filter((v, k) => k > chooseIdx)
      .map(v =>
        v.choices.map(v2 => {
          return {
            ...v2,
            parentId: v.id,
            parentLabel: v.title,
            title: `${v.title} => ${v2.label}`
          };
        })
      )
      .flat();
    console.log(item.targetQuestions);
  } else {
    const chooseIdx = questions.value.findIndex(i => i.sn === item.condition);
    item.targetQuestions = questions.value.filter((v, k) => k > chooseIdx);
  }
};

const saveLogic = async () => {
  const rules = [...logicSetting.rules];
  for (const index in rules) {
    const rule = rules[index];
    const num = Number(index) + 1;
    if (!rule.condition) {
      ElMessage.error(`第${num}条条件不能为空`);
      return;
    }
    if (!rule.choose) {
      ElMessage.error(`第${num}条选项不能为空`);
      return;
    }

    if (!rule.target) {
      ElMessage.error(`第${num}条条件结果不能为空`);
      return;
    }
  }
  rules.forEach(v => {
    v.question = v.method == "show" ? `QU${v.target}` : v.target;
    v.expression = `chooseOr(QU${v.condition},${v.choose})`;
  });
  console.log(rules);
  if (props.submitLogic) {
    props.submitLogic(rules);
    logicSetting.visible = false;
    return;
  }
};
</script>
<style lang="scss"></style>
