Jelajahi Sumber

复核页面:数据模型及获取

Michael Wang 4 tahun lalu
induk
melakukan
45000b9ebb

+ 90 - 2
src/api/inspectPage.ts

@@ -1,6 +1,94 @@
 import { httpApp } from "@/plugins/axiosApp";
 
+/** 清理复核任务 */
+export async function clearInspectedTask(
+  studentId?: string,
+  subjectCode?: string
+) {
+  const form = new FormData();
+  studentId && form.append("studentId", studentId);
+  subjectCode && form.append("subjectCode", subjectCode);
+  return httpApp.post("/admin/exam/inspected/clear", form);
+}
+
 /** 查看单个学生的复核任务 */
-export async function getSingleStudentTask(studentId: string) {
-  return httpApp.post("/admin/exam/inspected/getTask?studentId=" + studentId);
+export async function getSingleInspectedTask(studentId: string) {
+  // return httpApp.post("/admin/exam/inspected/getTask?studentId=" + studentId);
+  const form = new FormData();
+  studentId && form.append("studentId", studentId);
+  return httpApp.post("/admin/exam/inspected/getTask", form);
+}
+
+export interface InspectedParams {
+  subjectCode: string;
+  startScore?: string;
+  endScore?: string;
+  mainNumber?: string;
+  mainStartScore?: string;
+  mainEndScore?: string;
+  questionScore?: string;
+}
+
+/** 批量复核得到单个学生的复核任务 */
+export async function getOneOfInspectedTask({
+  subjectCode = "",
+  startScore = "",
+  endScore = "",
+  mainNumber = "",
+  mainStartScore = "",
+  mainEndScore = "",
+  questionScore = "",
+}: InspectedParams) {
+  const form = new FormData();
+  form.append("subjectCode", subjectCode);
+  form.append("startScore", startScore);
+  form.append("endScore", endScore);
+  form.append("mainNumber", mainNumber);
+  form.append("mainStartScore", mainStartScore);
+  form.append("mainEndScore", mainEndScore);
+  form.append("questionScore", questionScore);
+  return httpApp.post("/admin/exam/inspected/getTask", form);
+}
+
+/** 批量复核得到任务总数 */
+export async function getInspectedTaskStatus({
+  subjectCode = "",
+  startScore = "",
+  endScore = "",
+  mainNumber = "",
+  mainStartScore = "",
+  mainEndScore = "",
+  questionScore = "",
+}: InspectedParams) {
+  const form = new FormData();
+  form.append("subjectCode", subjectCode);
+  form.append("startScore", startScore);
+  form.append("endScore", endScore);
+  form.append("mainNumber", mainNumber);
+  form.append("mainStartScore", mainStartScore);
+  form.append("mainEndScore", mainEndScore);
+  form.append("questionScore", questionScore);
+  return httpApp.post("/admin/exam/inspected/getStatus", form);
+}
+
+/** 批量复核设置 */
+export async function getInspectedSetting() {
+  return httpApp.post("/admin/exam/inspected/getSetting");
+}
+
+/** 批量复核历史 */
+export async function getInspectedHistory({
+  subjectCode,
+  pageNumber = 1,
+  pageSize = 10,
+}: {
+  subjectCode: string;
+  pageNumber?: number; // 从1开始
+  pageSize?: number;
+}) {
+  const form = new FormData();
+  form.append("subjectCode", subjectCode);
+  form.append("pageNumber", pageNumber + "");
+  form.append("pageSize", pageSize + "");
+  return httpApp.post("/admin/exam/inspected/getHistory", form);
 }

+ 84 - 101
src/components/inspect/Inspect.vue

@@ -15,12 +15,18 @@
 </template>
 
 <script lang="ts">
-import { computed, defineComponent, onMounted, watch } from "vue";
-import { getSingleStudentTask } from "@/api/inspectPage";
+import { defineComponent, onMounted } from "vue";
+import {
+  clearInspectedTask,
+  getInspectedSetting,
+  getInspectedTaskStatus,
+  getOneOfInspectedTask,
+  getSingleInspectedTask,
+} from "@/api/inspectPage";
 import { store } from "./store";
 import MarkHeader from "./MarkHeader.vue";
+import { useRoute } from "vue-router";
 // import MarkBody from "./MarkBody.vue";
-import { useTimers } from "@/setups/useTimers";
 // import MarkHistory from "./MarkHistory.vue";
 
 export default defineComponent({
@@ -31,114 +37,91 @@ export default defineComponent({
     // MarkHistory,
   },
   setup: () => {
-    // const { addInterval } = useTimers();
-
-    // async function updateMarkTask() {
-    //   const settingRes = await clearMarkTask();
-    // }
-
-    // async function updateSetting() {
-    //   const settingRes = await getSetting();
-    //   // settingRes.data.uiSetting["answer.paper.scale"] ||= 1;
-    //   if (isEmpty(settingRes.data.uiSetting)) {
-    //     settingRes.data.uiSetting = {
-    //       "answer.paper.scale": 1,
-    //       "score.board.collapse": false,
-    //       "normal.mode": "keyboard",
-    //     } as Setting["uiSetting"];
-    //   }
-    //   store.setting = settingRes.data;
-    // }
-    // async function updateStatus() {
-    //   const res = await getStatus();
-    //   store.status = res.data;
-    // }
-    // async function updateGroups() {
-    //   const res = await getGroup();
-    //   store.groups = res.data;
-    // }
-    // async function updateTask() {
-    //   const res = await getTask();
-    //   if (res.data.libraryId) {
-    //     store.tasks.push(res.data);
-    //     store.currentTask = store.tasks[0];
-    //   }
-    // }
-
-    // // 5秒更新一次tasks
-    // addInterval(() => {
-    //   // console.log("get task", store.tasks);
-    //   if (store.tasks.length < 3) {
-    //     updateTask();
-    //   }
-    // }, 5 * 1000);
-
-    // // TODO: 后续改掉,不需要
-    // addInterval(() => {
-    //   updateStatus();
-    // }, 30 * 1000);
-
-    // onMounted(async () => {
-    //   await updateMarkTask();
-    //   updateSetting();
-    //   updateStatus();
-    //   updateGroups();
-    //   updateTask();
-    // });
-
-    // watch(
-    //   () => [store.setting.uiSetting, store.setting.mode],
-    //   () => {
-    //     updateUISetting(store.setting.mode, store.setting.uiSetting);
-    //   },
-    //   { deep: true }
-    // );
+    const route = useRoute();
+    let isSingleStudent = !!route.query.studentId;
+    const {
+      studentId,
+      subjectCode,
+      startScore,
+      endScore,
+      mainNumber,
+      mainStartScore,
+      mainEndScore,
+      questionScore,
+    } = route.query as {
+      studentId: string;
+      subjectCode: string;
+      startScore: string;
+      endScore: string;
+      mainNumber: string;
+      mainStartScore: string;
+      mainEndScore: string;
+      questionScore: string;
+    };
 
-    // const showMarkBoardTrack = computed(() => {
-    //   return store.setting.mode === ModeEnum.TRACK;
-    // });
+    async function updateClearTask() {
+      await clearInspectedTask(studentId, subjectCode);
+    }
 
-    // const showMarkBoardKeyBoard = computed(() => {
-    //   return (
-    //     store.setting.mode === ModeEnum.COMMON &&
-    //     store.setting.uiSetting["normal.mode"] === "keyboard"
-    //   );
-    // });
+    async function updateSetting() {
+      const settingRes = await getInspectedSetting();
+      store.setting.fileServer = settingRes.data.fileServer;
+      store.setting.userName = settingRes.data.userName;
+      store.setting.uiSetting = {
+        "answer.paper.scale": 1,
+        "score.board.collapse": false,
+      };
+    }
+    async function updateStatus() {
+      const res = await getInspectedTaskStatus({
+        subjectCode,
+        mainNumber,
+        startScore,
+        endScore,
+        mainStartScore,
+        mainEndScore,
+        questionScore,
+      });
+      if (res.data.valid) store.status = res.data;
+    }
+    async function updateTask() {
+      let res;
+      if (isSingleStudent) {
+        res = await getSingleStuTask();
+      } else {
+        res = await getOneOfStuTask();
+      }
+
+      store.currentTask = res.data;
+      if (store.currentTask) store.setting.subject = store.currentTask.subject;
+    }
 
-    // const showMarkBoardMouse = computed(() => {
-    //   return (
-    //     store.setting.mode === ModeEnum.COMMON &&
-    //     store.setting.uiSetting["normal.mode"] === "mouse"
-    //   );
-    // });
+    onMounted(async () => {
+      await updateClearTask();
 
-    // const saveTaskToServer = async () => {
-    //   console.log("save task to server");
-    //   const res = (await saveTask()) as any;
-    //   updateStatus();
-    //   if (res.data.success && store.currentTask) {
-    //     let { libraryId, studentId } = store.currentTask;
-    //     const i = store.markResults.findIndex(
-    //       (s) => s.libraryId === libraryId && s.studentId === studentId
-    //     );
-    //     store.markResults.splice(i, 1);
-    //     store.currentTask = undefined;
-    //     store.tasks.shift();
-    //   } else {
-    //     console.log(res.data.message);
-    //   }
-    // };
+      updateSetting();
+      updateStatus();
+      updateTask();
+    });
 
     async function getSingleStuTask() {
-      return getSingleStudentTask("1581");
+      return getSingleInspectedTask(studentId);
+    }
+
+    async function getOneOfStuTask() {
+      return getOneOfInspectedTask({
+        subjectCode,
+        mainNumber,
+        startScore,
+        endScore,
+        mainStartScore,
+        mainEndScore,
+        questionScore,
+      });
     }
-    console.log(getSingleStuTask());
     return {
       store,
       // saveTaskToServer,
-      // showMarkBoardTrack,
-      // showMarkBoardKeyBoard,
-      // showMarkBoardMouse,
     };
   },
 });

+ 59 - 70
src/components/inspect/MarkHeader.vue

@@ -1,10 +1,10 @@
 <template>
   <div
-    class="tw-flex tw-gap-4 tw-justify-between tw-items-center header-bg"
-    style="z-index: 10000; position: relative; font-size: 16px; height: 40px"
+    class="tw-flex tw-gap-4 tw-justify-between tw-items-center header-container"
+    v-if="store.setting"
   >
     <div>
-      {{ store.setting.subject?.name }}
+      {{ store.setting.subject.name }}
     </div>
     <div class="tw-flex tw-gap-1">
       <div>
@@ -14,45 +14,45 @@
       </div>
     </div>
     <ul class="tw-flex tw-gap-2 tw-mb-0">
-      <li @click="upScale" title="放大" style="line-height: 20px">
+      <li>
+        待复核<span class="highlight-text">{{ store.status.totalCount }}</span>
+      </li>
+    </ul>
+    <ul class="tw-flex tw-gap-2 tw-mb-0">
+      <li @click="upScale" title="放大" class="line-height-20">
         <PlusCircleOutlined
-          style="font-size: 20px"
+          class="icon-font-size-20"
           :style="{
             color: greaterThanOneScale ? 'red' : 'white',
           }"
         />
       </li>
-      <li @click="downScale" title="缩小" style="line-height: 20px">
+      <li @click="downScale" title="缩小" class="line-height-20">
         <MinusCircleOutlined
-          style="font-size: 20px"
+          class="icon-font-size-20"
           :style="{
             color: lessThanOneScale ? 'red' : 'white',
           }"
         />
       </li>
-      <li @click="normalScale" title="适应" style="line-height: 20px">
-        <FullscreenOutlined style="font-size: 20px" />
+      <li @click="normalScale" title="适应" class="line-height-20">
+        <FullscreenOutlined class="icon-font-size-20" />
       </li>
     </ul>
-    <div @click="toggleSettingMode" style="line-height: 20px">
-      {{ modeName }} {{ store.setting.forceMode ? "" : "(切换)" }}
-    </div>
-    <div @click="toggleHistory" style="line-height: 20px" title="回看">
-      <HistoryOutlined style="font-size: 20px" />
+    <div @click="toggleHistory" class="line-height-20" title="回看">
+      <HistoryOutlined class="icon-font-size-20" />
     </div>
     <div class="tw-flex tw-place-items-center">
-      <UserOutlined style="font-size: 18px; line-height: 18px" />{{
-        store.setting.userName
-      }}
+      <UserOutlined class="icon-with-text" />{{ store.setting.userName }}
     </div>
     <div class="tw-flex tw-place-items-center">
-      <PoweroffOutlined style="font-size: 18px; line-height: 18px" />退出
+      <PoweroffOutlined class="icon-with-text" />关闭
     </div>
   </div>
 </template>
 
 <script lang="ts">
-import { getGroups, getHistoryTask } from "@/api/markPage";
+import { getInspectedHistory } from "@/api/inspectPage";
 import { computed, defineComponent } from "vue";
 import { store } from "./store";
 import {
@@ -66,6 +66,7 @@ import {
   QuestionCircleOutlined,
 } from "@ant-design/icons-vue";
 import { ModeEnum } from "@/types";
+import { useRoute } from "vue-router";
 
 export default defineComponent({
   name: "MarkHeader",
@@ -80,36 +81,27 @@ export default defineComponent({
     QuestionCircleOutlined,
   },
   setup() {
-    const modeName = computed(() =>
-      store.setting.mode === ModeEnum.TRACK ? "轨迹模式" : "普通模式"
-    );
-    function toggleSettingMode() {
-      if (store.setting.mode === ModeEnum.TRACK) {
-        store.setting.mode = ModeEnum.COMMON;
-      } else {
-        store.setting.mode = ModeEnum.TRACK;
-      }
-      if (store.currentMarkResult) {
-        store.currentMarkResult.scoreList = [];
-        store.currentMarkResult.trackList = [];
-      }
-      if (store.currentTask) {
-        store.currentTask.questionList.forEach((q) => (q.score = null));
-      }
-      store.currentQuestion = undefined;
-      store.currentScore = undefined;
-    }
-    const progress = computed(() => {
-      const { totalCount, markedCount } = store.status;
-      if (totalCount <= 0) return 0;
-      let p = markedCount / totalCount;
-      if (p < 0.01 && markedCount >= 1) p = 0.01;
-      p = Math.floor(p * 100);
-      return p;
-    });
-    const group = computed(() => {
-      return store.groups.find((g) => g.number === store.setting.groupNumber);
-    });
+    const route = useRoute();
+    let isSingleStudent = !!route.params.studentId;
+    const {
+      studentId,
+      subjectCode,
+      startScore,
+      endScore,
+      mainNumber,
+      mainStartScore,
+      mainEndScore,
+      questionScore,
+    } = route.query as {
+      studentId: string;
+      subjectCode: string;
+      startScore: string;
+      endScore: string;
+      mainNumber: string;
+      mainStartScore: string;
+      mainEndScore: string;
+      questionScore: string;
+    };
 
     const upScale = () => {
       const s = store.setting.uiSetting["answer.paper.scale"];
@@ -134,30 +126,17 @@ export default defineComponent({
       return store.setting.uiSetting["answer.paper.scale"] < 1;
     });
 
-    async function switchGroupDialog() {
-      const groups = await getGroups();
-      console.log(groups);
-    }
-
     async function updateHistoryTask({
       pageNumber = 1,
       pageSize = 10,
-      order = "markerTime",
-      sort = "DESC",
-      secretNumber = null,
     }: {
       pageNumber: number; // 从1开始
       pageSize: number;
-      order: "markerTime" | "markerScore";
-      sort: "ASC" | "DESC";
-      secretNumber: string | null;
     }) {
-      const res = await getHistoryTask({
+      const res = await getInspectedHistory({
         pageNumber,
         pageSize,
-        order,
-        sort,
-        secretNumber,
+        subjectCode,
       });
       if (res.data) {
         store.historyTasks.push(res.data);
@@ -166,10 +145,6 @@ export default defineComponent({
 
     return {
       store,
-      modeName,
-      toggleSettingMode,
-      progress,
-      group,
       upScale,
       downScale,
       normalScale,
@@ -177,18 +152,32 @@ export default defineComponent({
       lessThanOneScale,
       updateHistoryTask,
       toggleHistory,
-      switchGroupDialog,
     };
   },
 });
 </script>
 
 <style scoped>
-.header-bg {
+.header-container {
+  z-index: 10000;
+  position: relative;
+  font-size: 16px;
+  height: 40px;
+
   background-color: #5d6d7d;
   color: white;
 }
 .highlight-text {
   color: #ffe400;
 }
+.icon-font-size-20 {
+  font-size: 20px;
+}
+.line-height-20 {
+  line-height: 20px;
+}
+.icon-with-text {
+  font-size: 18px;
+  line-height: 18px;
+}
 </style>

+ 7 - 28
src/components/inspect/store.ts

@@ -1,44 +1,23 @@
-import { ModeEnum, Setting, MarkStore, Task } from "@/types";
-import { reactive, watch } from "vue";
+import { InspectStore, Task } from "@/types";
+import { reactive } from "vue";
 
 const obj = {
   setting: {
-    mode: "TRACK",
-    examType: "SCAN_IMAGE",
-    forceMode: false,
-    sheetView: false,
-    sheetConfig: [],
-    enableAllZero: false,
     fileServer: "",
     userName: "",
-    subject: <Setting["subject"]>{},
-    forceSpecialTag: false,
+    subject: { name: "", code: "" },
     uiSetting: {
       "answer.paper.scale": 1,
       "score.board.collapse": false,
-      "normal.mode": "keyboard",
     },
-    statusValue: "FORMAL",
-    problemTypes: [],
-    groupNumber: 0,
-    topCount: 0,
-    splitConfig: [],
-    prefetchCount: 3,
-    startTime: 0,
-    endTime: 0,
   },
-  status: <MarkStore["status"]>{},
-  groups: [],
-  tasks: [],
-  currentMarkResult: undefined,
+  status: {
+    totalCount: 0,
+  },
   currentTask: <Task>{},
-  currentQuestion: undefined,
-  currentScore: undefined,
-  markResults: [],
   historyOpen: false,
   MarkBoardTrackCollapse: false,
   historyTasks: [],
-  removeScoreTracks: [],
-} as MarkStore;
+} as InspectStore;
 
 export const store = reactive(obj);

+ 19 - 0
src/types/index.ts

@@ -158,3 +158,22 @@ export interface MarkResult {
   problem: boolean;
   problemTypeId: number;
 }
+
+export interface InspectStore {
+  setting: {
+    fileServer: string;
+    userName: string;
+    subject: { name: string; code: string };
+    uiSetting: {
+      "answer.paper.scale": number;
+      "score.board.collapse": boolean;
+    };
+  };
+  status: {
+    totalCount: number; //总数量
+  };
+  currentTask?: Task; // 用来切换task,还有回看
+  historyOpen: boolean; // 是否打开回评侧边栏
+  MarkBoardTrackCollapse: boolean; // 是否收缩评分版
+  historyTasks: Array<Task>;
+}