|
@@ -0,0 +1,275 @@
|
|
|
+import { numberToChinese } from "@/plugins/utils";
|
|
|
+import {
|
|
|
+ getModel as createFillQuestion,
|
|
|
+ getFullModel as getFillQuesitonElements,
|
|
|
+} from "../../../../card/elements/fill-question/model";
|
|
|
+import {
|
|
|
+ getModel as createFillLine,
|
|
|
+ getFullModel as getFillLineElements,
|
|
|
+} from "../../../../card/elements/fill-line/model";
|
|
|
+import {
|
|
|
+ getModel as createExplain,
|
|
|
+ getFullModel as getExplainElements,
|
|
|
+} from "../../../../card/elements/explain/model";
|
|
|
+
|
|
|
+const COMMON_QUESTION_TYPES = [
|
|
|
+ "SINGLE_ANSWER_QUESTION",
|
|
|
+ "MULTIPLE_ANSWER_QUESTION",
|
|
|
+ "BOOL_ANSWER_QUESTION",
|
|
|
+ "FILL_BLANK_QUESTION",
|
|
|
+ "TEXT_ANSWER_QUESTION",
|
|
|
+];
|
|
|
+
|
|
|
+const structTypeToCardElementType = {
|
|
|
+ SINGLE_ANSWER_QUESTION: "FILL_QUESTION",
|
|
|
+ MULTIPLE_ANSWER_QUESTION: "FILL_QUESTION",
|
|
|
+ BOOL_ANSWER_QUESTION: "FILL_QUESTION",
|
|
|
+ FILL_BLANK_QUESTION: "FILL_LINE",
|
|
|
+ TEXT_ANSWER_QUESTION: "EXPLAIN",
|
|
|
+};
|
|
|
+
|
|
|
+const elementModel = {
|
|
|
+ FILL_QUESTION: (presetData) => {
|
|
|
+ const model = createFillQuestion(presetData);
|
|
|
+ return getFillQuesitonElements(model, {
|
|
|
+ pageSize: presetData.pageSize,
|
|
|
+ columnNumber: presetData.columnNumber,
|
|
|
+ });
|
|
|
+ },
|
|
|
+ FILL_LINE: (presetData) => {
|
|
|
+ const model = createFillLine(presetData);
|
|
|
+ return getFillLineElements(model);
|
|
|
+ },
|
|
|
+ EXPLAIN: (presetData) => {
|
|
|
+ const model = createExplain(presetData);
|
|
|
+ return getExplainElements(model);
|
|
|
+ },
|
|
|
+};
|
|
|
+
|
|
|
+function parsePaperStruct(paperJson) {
|
|
|
+ let structList = [];
|
|
|
+ paperJson.paperDetails.forEach((detail) => {
|
|
|
+ const commonQuestions = detail.paperDetailUnits.filter((q) =>
|
|
|
+ COMMON_QUESTION_TYPES.includes(q.questionType)
|
|
|
+ );
|
|
|
+ if (commonQuestions.length) {
|
|
|
+ const commonStructList = getCommonQuestionStructList(
|
|
|
+ detail,
|
|
|
+ commonQuestions,
|
|
|
+ true,
|
|
|
+ 0
|
|
|
+ );
|
|
|
+ structList.push(...commonStructList);
|
|
|
+ }
|
|
|
+
|
|
|
+ const nestedQuestions = detail.paperDetailUnits.filter(
|
|
|
+ (q) => !COMMON_QUESTION_TYPES.includes(q.questionType)
|
|
|
+ );
|
|
|
+ if (nestedQuestions.length) {
|
|
|
+ const nestedStructList = getNestedQuestionStructList(
|
|
|
+ detail,
|
|
|
+ nestedQuestions
|
|
|
+ );
|
|
|
+ structList.push(...nestedStructList);
|
|
|
+ }
|
|
|
+ });
|
|
|
+
|
|
|
+ structList.sort((a, b) => a.sortNo - b.sortNo);
|
|
|
+ console.log(structList);
|
|
|
+ return structList;
|
|
|
+}
|
|
|
+
|
|
|
+function getCommonQuestionStructList(
|
|
|
+ detail,
|
|
|
+ questions,
|
|
|
+ isCommon,
|
|
|
+ nestedQNo = 0
|
|
|
+) {
|
|
|
+ let structList = [];
|
|
|
+ let structs = {};
|
|
|
+ const qTypeNum = isCommon ? 1 : 2;
|
|
|
+ questions.forEach((question) => {
|
|
|
+ if (!structs[question.questionType]) structs[question.questionType] = [];
|
|
|
+ structs[question.questionType].push(question);
|
|
|
+ });
|
|
|
+ Object.keys(structs).forEach((structType) => {
|
|
|
+ const typeNo = COMMON_QUESTION_TYPES.indexOf(structType) + 1;
|
|
|
+ const questions = parseCommonTypeQuestions(structType, structs[structType]);
|
|
|
+
|
|
|
+ structList.push({
|
|
|
+ detailName: detail.name,
|
|
|
+ detailNo: detail.number,
|
|
|
+ structType,
|
|
|
+ isCommon,
|
|
|
+ nestedQNo,
|
|
|
+ sortNo:
|
|
|
+ typeNo * 10000 + detail.number * 1000 + qTypeNum * 100 + nestedQNo,
|
|
|
+ questions,
|
|
|
+ });
|
|
|
+ });
|
|
|
+ return structList;
|
|
|
+}
|
|
|
+
|
|
|
+function getNestedQuestionStructList(detail, questions) {
|
|
|
+ let structList = [];
|
|
|
+ questions.forEach((question) => {
|
|
|
+ const qStructList = getCommonQuestionStructList(
|
|
|
+ detail,
|
|
|
+ question.question.subQuestions.map((q) => {
|
|
|
+ return {
|
|
|
+ number: q.subNumber,
|
|
|
+ questionType: q.questionType,
|
|
|
+ question: q,
|
|
|
+ };
|
|
|
+ }),
|
|
|
+ false,
|
|
|
+ question.number
|
|
|
+ );
|
|
|
+ structList.push(...qStructList);
|
|
|
+ });
|
|
|
+ return structList;
|
|
|
+}
|
|
|
+
|
|
|
+function parseCommonTypeQuestions(structType, dataList) {
|
|
|
+ const choiceQs = [
|
|
|
+ "SINGLE_ANSWER_QUESTION",
|
|
|
+ "MULTIPLE_ANSWER_QUESTION",
|
|
|
+ "BOOL_ANSWER_QUESTION",
|
|
|
+ ];
|
|
|
+ let questions = [];
|
|
|
+ if (choiceQs.includes(structType)) {
|
|
|
+ questions = dataList.map((item) => {
|
|
|
+ return {
|
|
|
+ questionNo: item.number,
|
|
|
+ optionCount:
|
|
|
+ structType === "BOOL_ANSWER_QUESTION"
|
|
|
+ ? 2
|
|
|
+ : item.question.quesOptions.length,
|
|
|
+ };
|
|
|
+ });
|
|
|
+ } else if (structType === "FILL_BLANK_QUESTION") {
|
|
|
+ questions = dataList.map((item) => {
|
|
|
+ return {
|
|
|
+ questionNo: item.number,
|
|
|
+ fillCount: getFillBackClozeCount(item.question.quesBody),
|
|
|
+ };
|
|
|
+ });
|
|
|
+ } else {
|
|
|
+ questions = dataList.map((item) => item.number);
|
|
|
+ }
|
|
|
+ return questions;
|
|
|
+}
|
|
|
+
|
|
|
+export function getFillBackClozeCount(questionBodyContent) {
|
|
|
+ let questionBody = null;
|
|
|
+ let num = 0;
|
|
|
+ try {
|
|
|
+ questionBody = JSON.parse(questionBodyContent);
|
|
|
+ questionBody.sections.forEach((section) => {
|
|
|
+ section.blocks.forEach((block) => {
|
|
|
+ if (block.type === "cloze") num++;
|
|
|
+ });
|
|
|
+ });
|
|
|
+ } catch (error) {
|
|
|
+ num = 1;
|
|
|
+ }
|
|
|
+
|
|
|
+ return num;
|
|
|
+}
|
|
|
+
|
|
|
+export function buildCardElements(structList, elementTypePreSetInfo = {}) {
|
|
|
+ let cardElements = [];
|
|
|
+ structList.forEach((struct) => {
|
|
|
+ const detailChineseNumber = numberToChinese(struct.detailNo);
|
|
|
+ let topicName =
|
|
|
+ struct.isCommon || (!struct.isCommon && struct.isOnlyOneNested)
|
|
|
+ ? `${detailChineseNumber}、${struct.detailName}`
|
|
|
+ : `${detailChineseNumber}(${struct.nestedQNo})`;
|
|
|
+ const modelType = structTypeToCardElementType[struct.structType];
|
|
|
+ const elementTypePreSet = elementTypePreSetInfo[modelType] || {};
|
|
|
+
|
|
|
+ if (!struct.isCommon && struct.structType === "TEXT_ANSWER_QUESTION") {
|
|
|
+ struct.questions.forEach((qno) => {
|
|
|
+ const presetData = {
|
|
|
+ ...elementTypePreSet,
|
|
|
+ topicName: `${topicName}、${qno}`,
|
|
|
+ paperStruct: { ...struct, questions: [qno] },
|
|
|
+ };
|
|
|
+
|
|
|
+ const elements = elementModel[modelType](presetData);
|
|
|
+ cardElements.push(...elements);
|
|
|
+ });
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ let presetData = {
|
|
|
+ ...elementTypePreSet,
|
|
|
+ topicName,
|
|
|
+ paperStruct: struct,
|
|
|
+ };
|
|
|
+ if (struct.structType === "MULTIPLE_ANSWER_QUESTION")
|
|
|
+ presetData.isMultiply = true;
|
|
|
+ if (struct.structType === "BOOL_ANSWER_QUESTION")
|
|
|
+ presetData.isBoolean = true;
|
|
|
+
|
|
|
+ const elements = elementModel[modelType](presetData);
|
|
|
+ cardElements.push(...elements);
|
|
|
+ });
|
|
|
+
|
|
|
+ return cardElements;
|
|
|
+}
|
|
|
+
|
|
|
+export function buildPaperCard(paperJson) {
|
|
|
+ const structList = parsePaperStruct(paperJson);
|
|
|
+ const cardElements = buildCardElements(structList);
|
|
|
+ // console.log(cardElements);
|
|
|
+ return cardElements;
|
|
|
+}
|
|
|
+
|
|
|
+// const paperStruct = {
|
|
|
+// paperName: "",
|
|
|
+// structList: [
|
|
|
+// {
|
|
|
+// detailName: "",
|
|
|
+// detailNo: 1,
|
|
|
+// structType: 1,
|
|
|
+// questions: [
|
|
|
+// { questionNo: "1", optionCount: 4 },
|
|
|
+// { questionNo: "2", optionCount: 4 },
|
|
|
+// ],
|
|
|
+// },
|
|
|
+// {
|
|
|
+// detailName: "",
|
|
|
+// detailNo: 1,
|
|
|
+// structType: 2,
|
|
|
+// questions: [
|
|
|
+// { questionNo: "3", optionCount: 4 },
|
|
|
+// { questionNo: "4", optionCount: 4 },
|
|
|
+// ],
|
|
|
+// },
|
|
|
+// {
|
|
|
+// detailName: "",
|
|
|
+// detailNo: 1,
|
|
|
+// structType: 3,
|
|
|
+// questions: [
|
|
|
+// { questionNo: "5", optionCount: 2 },
|
|
|
+// { questionNo: "6", optionCount: 2 },
|
|
|
+// ],
|
|
|
+// },
|
|
|
+// {
|
|
|
+// detailName: "",
|
|
|
+// detailNo: 1,
|
|
|
+// structType: 4,
|
|
|
+// questions: [
|
|
|
+// { questionNo: "7", fillCount: 1 },
|
|
|
+// { questionNo: "8", fillCount: 2 },
|
|
|
+// ],
|
|
|
+// },
|
|
|
+// {
|
|
|
+// detailName: "",
|
|
|
+// detailNo: 1,
|
|
|
+// structType: 5,
|
|
|
+// questions: ["11", "12"],
|
|
|
+// },
|
|
|
+// ],
|
|
|
+// };
|