From 99ce738f54855db65459b5306e4979134dc23d63 Mon Sep 17 00:00:00 2001 From: ZhangXianQiang <1135831638@qq.com> Date: 星期四, 04 七月 2024 18:37:08 +0800 Subject: [PATCH] feat:试卷查看 --- src/views/grade/components/answer-main/answer-determine/index.vue | 142 ++++++++++++++++++++ src/views/grade/components/answer-main/answer-single/index.vue | 2 src/views/grade/components/answer-main/answer-fill/index.vue | 125 +++++++++++++++++ src/views/grade/components/answer-main/answer-count/index.vue | 50 +++++++ src/views/grade/components/answer-main/answer-short/index.vue | 57 ++++++++ src/views/grade/index.vue | 11 + 6 files changed, 385 insertions(+), 2 deletions(-) diff --git a/src/views/grade/components/answer-main/answer-count/index.vue b/src/views/grade/components/answer-main/answer-count/index.vue new file mode 100644 index 0000000..bca7347 --- /dev/null +++ b/src/views/grade/components/answer-main/answer-count/index.vue @@ -0,0 +1,50 @@ +<!-- 璁$畻棰� --> +<template> + <div class="answer-container w-full h-full"> + <el-scrollbar> + <ExamInfo class="mb-5" :questionIndex="currentIndex" :activeQuestion="activeQuestion"></ExamInfo> + + <div class="answer-content"> + <vue-ueditor-wrap v-model="content" editor-id="editor" :config="editorConfig" + :editorDependencies="['ueditor.config.js', 'ueditor.all.js']" /> + </div> + </el-scrollbar> + </div> +</template> + +<script setup> +import { ref,watchEffect } from 'vue'; +import { storeToRefs } from 'pinia'; +import ExamInfo from '@/components/ExamInfo/index.vue'; +import { useExamStore } from '@/store/index.js'; + +const examStore = useExamStore(); + +const editorConfig = { + // 鍚庣鏈嶅姟鍦板潃锛屽悗绔鐞嗗弬鑰� + // https://open-doc.modstart.com/ueditor-plus/backend.html + serverUrl: '/api/path/to/server', + UEDITOR_HOME_URL: '/static/UEditorPlus/', + UEDITOR_CORS_URL: '/static/UEditorPlus/', + initialFrameWidth: '95%', + initialFrameHeight: 400, + toolbars: [ + ['fullscreen', 'undo','redo', '|', 'fontfamily', 'fontsize', '|', + 'forecolor', 'backcolor', 'bold', 'italic', 'underline','strikethrough','|', + 'removeformat', 'formatmatch', 'autotypeset', 'blockquote', 'pasteplain', '|', + 'inserttable', 'deletetable', 'insertparagraph', 'insertrow', 'deleterow', + 'insertcol', 'deletecol','mergecells','mergerow','mergecol', 'splittocells', + 'splittorows','splittocols', '|', 'formula'] + ] +}; + +const { currentType, currentIndex } = storeToRefs(examStore); + +const activeQuestion = ref(examStore.getActiveQuestion); +const content = ref(activeQuestion.value.answer); + +</script> + +<style lang="scss" scoped> + +</style> \ No newline at end of file diff --git a/src/views/grade/components/answer-main/answer-determine/index.vue b/src/views/grade/components/answer-main/answer-determine/index.vue new file mode 100644 index 0000000..5f23935 --- /dev/null +++ b/src/views/grade/components/answer-main/answer-determine/index.vue @@ -0,0 +1,142 @@ +<!-- 鍒ゆ柇棰� --> +<template> + <div class="answer-container w-full h-full"> + <el-scrollbar class="flex-1 mr-4"> + <ExamInfo class="mb-5" :questionIndex="currentIndex" :activeQuestion="activeQuestion"></ExamInfo> + + <div class="answer-content"> + <div class="answer-item flex" v-for="item, index in activeQuestion.questionItemList" :class="answerState(item)"> + <div class="answer-icon flex flex-col justify-center items-center flex-shrink-0">{{ item.prefix }}</div> + <div class="answer-text text-gray-700" v-html="item.content"></div> + </div> + </div> + + </el-scrollbar> + + <el-scrollbar class="flex-1 ml-4"> + <div class="analysis-container"> + <div class="analysis-item" :class="analysisState"> + <div class="item-label">鎮ㄧ殑绛旀</div> + <div class="item-info">{{ activeQuestion.answer }}</div> + </div> + + <div class="analysis-item analysis-right"> + <div class="item-label">姝g‘绛旀</div> + <div class="item-info">{{ activeQuestion.questionAnswer }}</div> + </div> + + <div class="analysis-item text-gray-700"> + <div class="item-label">瑙f瀽</div> + <div class="item-info" v-html="activeQuestion.analyze"></div> + </div> + </div> + </el-scrollbar> + </div> +</template> + +<script setup> +import { ref, computed } from 'vue'; +import { storeToRefs } from 'pinia'; +import ExamInfo from '@/components/ExamInfo/index.vue'; +import { useExamStore } from '@/store/index.js'; +const examStore = useExamStore(); + +const { currentType, currentIndex } = storeToRefs(examStore); + +const activeQuestion = ref(examStore.getActiveQuestion); + + +const answerState = (item) => { + if (activeQuestion.value.answer === item.prefix) { + item.isActive = true; + } + return { + active: item.isActive || item.prefix === activeQuestion.value.answer + }; +}; + +const analysisState = computed(() => { + return { + 'analysis-right': activeQuestion.value.isRight, + 'analysis-wrong': !activeQuestion.value.isRight + }; +}); +</script> + +<style lang="scss" scoped> +.answer-container { + --right-color: #67c23a; + --wrong-color: #f56c6c; +} + +.answer-item { + max-width: 500px; + border-radius: 10px; + border: 1px solid #DCDFE6; + overflow: hidden; + margin-bottom: 20px; + + &:last-of-type { + margin-bottom: 0; + } + + + .answer-icon { + width: 50px; + background-color: #F0F2F5; + border-right: 1px solid #ffffff; + } + + .answer-text { + min-height: 50px; + padding: 15px 0; + margin: 0 10px; + } +} + +.right { + border-color: var(--right-color) !important; + background-color: rgba($color: #67c23a, $alpha: 0.2) !important; + + .answer-icon { + color: #ffffff !important; + border-color: var(--right-color) !important; + background-color: var(--right-color) !important; + } + + .answer-text { + color: var(--right-color) !important; + } +} + +.wrong { + border-color: var(--wrong-color) !important; + background-color: rgba($color: #f56c6c, $alpha: 0.2) !important; + + .answer-icon { + color: #ffffff !important; + border-color: var(--wrong-color) !important; + background-color: var(--wrong-color) !important; + } + + .answer-text { + color: var(--wrong-color) !important; + } +} + +.analysis-item { + margin-bottom: 10px; + + .item-label { + font-weight: bold; + } +} + +.analysis-right { + color: var(--right-color); +} + +.analysis-wrong { + color: var(--wrong-color); +} +</style> \ No newline at end of file diff --git a/src/views/grade/components/answer-main/answer-fill/index.vue b/src/views/grade/components/answer-main/answer-fill/index.vue new file mode 100644 index 0000000..2546644 --- /dev/null +++ b/src/views/grade/components/answer-main/answer-fill/index.vue @@ -0,0 +1,125 @@ +<!-- 濉┖棰� --> +<template> + <div class="answer-container w-full h-full"> + <el-scrollbar> + <ExamInfo class="mb-5" :questionIndex="currentIndex" :activeQuestion="activeQuestion"></ExamInfo> + + <div class="answer-content"> + <div class="answer-item flex" v-for="item, index in activeQuestion.questionItemList" :class="answerState(item,index)"> + <div class="answer-icon flex flex-col justify-center items-center flex-shrink-0">{{ item.prefix }}</div> + <div class="answer-text text-gray-700" v-html="item.content"></div> + </div> + </div> + + </el-scrollbar> + </div> +</template> + +<script setup> +import { ref,computed } from 'vue'; +import { storeToRefs } from 'pinia'; +import ExamInfo from '@/components/ExamInfo/index.vue'; +import { useExamStore } from '@/store/index.js'; +const examStore = useExamStore(); + + + +const { currentType, currentIndex } = storeToRefs(examStore); + +const activeQuestion = ref(examStore.getActiveQuestion); + + +const answerState = (item,index) => { + if(Array.isArray(activeQuestion.value.answerList) && activeQuestion.value.answerList[index]) { + item.isActive = true; + } + return { + active: item.isActive + }; +}; + +const analysisState = computed(() => { + return { + 'analysis-right': activeQuestion.value.isRight, + 'analysis-wrong': !activeQuestion.value.isRight + }; +}); +</script> + +<style lang="scss" scoped> +.answer-container { + --right-color: #67c23a; + --wrong-color: #f56c6c; +} + +.answer-item { + max-width: 500px; + border-radius: 10px; + border: 1px solid #DCDFE6; + overflow: hidden; + margin-bottom: 20px; + + &:last-of-type { + margin-bottom: 0; + } + + + .answer-icon { + width: 50px; + background-color: #F0F2F5; + border-right: 1px solid #ffffff; + } + + .answer-text { + min-height: 50px; + padding: 15px 0; + margin: 0 10px; + } +} + +.right { + border-color: var(--right-color) !important; + background-color: rgba($color: #67c23a, $alpha: 0.2) !important; + + .answer-icon { + color: #ffffff !important; + border-color: var(--right-color) !important; + background-color: var(--right-color) !important; + } + + .answer-text { + color: var(--right-color) !important; + } +} + +.wrong { + border-color: var(--wrong-color) !important; + background-color: rgba($color: #f56c6c, $alpha: 0.2) !important; + + .answer-icon { + color: #ffffff !important; + border-color: var(--wrong-color) !important; + background-color: var(--wrong-color) !important; + } + + .answer-text { + color: var(--wrong-color) !important; + } +} + +.analysis-item { + margin-bottom: 10px; + + .item-label { + font-weight: bold; + } +} + +.analysis-right { + color: var(--right-color); +} + +.analysis-wrong { + color: var(--wrong-color); +} +</style> \ No newline at end of file diff --git a/src/views/grade/components/answer-main/answer-short/index.vue b/src/views/grade/components/answer-main/answer-short/index.vue new file mode 100644 index 0000000..e5f4d49 --- /dev/null +++ b/src/views/grade/components/answer-main/answer-short/index.vue @@ -0,0 +1,57 @@ +<!-- 绠�绛旈 --> +<template> + <div class="answer-container w-full h-full"> + <el-scrollbar> + <ExamInfo class="mb-5" :questionIndex="currentIndex" :activeQuestion="activeQuestion"></ExamInfo> + + <div class="answer-content"> + <vue-ueditor-wrap v-model="content" editor-id="editor" :config="editorConfig" + :editorDependencies="['ueditor.config.js', 'ueditor.all.js']" /> + </div> + <el-button @click="testClick">鍐呭鏄剧ず</el-button> + </el-scrollbar> + </div> +</template> + +<script setup> +import { ref,watchEffect } from 'vue'; +import { storeToRefs } from 'pinia'; +import ExamInfo from '@/components/ExamInfo/index.vue'; +import { useExamStore } from '@/store/index.js'; + +const examStore = useExamStore(); + +const editorConfig = { + // 鍚庣鏈嶅姟鍦板潃锛屽悗绔鐞嗗弬鑰� + // https://open-doc.modstart.com/ueditor-plus/backend.html + serverUrl: '/api/path/to/server', + UEDITOR_HOME_URL: '/static/UEditorPlus/', + UEDITOR_CORS_URL: '/static/UEditorPlus/', + initialFrameWidth: '95%', + initialFrameHeight: 400, + toolbars: [ + ['fullscreen', 'undo','redo', '|', 'fontfamily', 'fontsize', '|', + 'forecolor', 'backcolor', 'bold', 'italic', 'underline','strikethrough','|', + 'removeformat', 'formatmatch', 'autotypeset', 'blockquote', 'pasteplain', '|', + 'inserttable', 'deletetable', 'insertparagraph', 'insertrow', 'deleterow', + 'insertcol', 'deletecol','mergecells','mergerow','mergecol', 'splittocells', + 'splittorows','splittocols', '|', 'formula'] + ] +}; + +const { currentType, currentIndex } = storeToRefs(examStore); + +const activeQuestion = ref(examStore.getActiveQuestion); +const content = ref(activeQuestion.value.answer); + +const testClick = () => { + console.log(content.value); +} +watchEffect(() => { + examStore.setQuestionAnswer(currentType.value, currentIndex.value, content.value); +}) +</script> + +<style lang="scss" scoped> + +</style> \ No newline at end of file diff --git a/src/views/grade/components/answer-main/answer-single/index.vue b/src/views/grade/components/answer-main/answer-single/index.vue index dd7706c..9b6e3aa 100644 --- a/src/views/grade/components/answer-main/answer-single/index.vue +++ b/src/views/grade/components/answer-main/answer-single/index.vue @@ -6,7 +6,7 @@ <div class="answer-content"> <div class="answer-item flex" v-for="item, index in activeQuestion.questionItemList" :class="answerState(item)"> <div class="answer-icon flex flex-col justify-center items-center flex-shrink-0">{{ item.prefix }}</div> - <div class="answer-text text-gray-700">{{ item.content }}</div> + <div class="answer-text text-gray-700" v-html="item.content"></div> </div> </div> </el-scrollbar> diff --git a/src/views/grade/index.vue b/src/views/grade/index.vue index e3ef142..b7ad27e 100644 --- a/src/views/grade/index.vue +++ b/src/views/grade/index.vue @@ -85,6 +85,10 @@ import AnswerSingle from './components/answer-main/answer-single/index.vue'; import AnswerMultiple from './components/answer-main/answer-multiple/index.vue'; import AnswerAudio from './components/answer-main/answer-audio/index.vue'; +import AnswerFill from './components/answer-main/answer-fill/index.vue'; +import AnswerDetermine from './components/answer-main/answer-determine/index.vue'; +import AnswerShort from './components/answer-main/answer-short/index.vue'; +import AnswerCount from './components/answer-main/answer-count/index.vue'; import { useGradeStore } from '@/store/index.js'; import { useRouter } from 'vue-router'; @@ -97,7 +101,12 @@ const typeComponent = { 1: AnswerSingle, 2: AnswerMultiple, - 3: AnswerAudio, + 3: AnswerDetermine, + 4: AnswerFill, + 5: AnswerShort, + 6: AnswerAudio, + 7: AnswerCount, + 8: AnswerShort, }; -- Gitblit v1.8.0