dbsd_kczx/src/views/kc/wjxCswj/WjxCywjV2Dtjg.vue

663 lines
24 KiB
Vue
Raw Normal View History

2024-08-19 08:37:20 +08:00
<template>
<div id="siteMain">
2024-08-19 08:37:20 +08:00
<div id="maxSite">
<a-layout>
<!-- 页头 -->
<headerPage />
<!-- 主体部分 -->
<a-layout-content style="background-color: white; margin-top: 10px">
<a-row>
<a-col :span="24" style="text-align: center">
<span class="title">{{ zyInfo.title }}</span>
</a-col>
2024-10-15 18:21:39 +08:00
<a-col :span="24" style="text-align: right">
<span style="color: #999">开始时间</span><span style="color: #666">{{ dayjs(zyInfo.startTime).format('MM.DD HH:mm') }}</span> ~
<span style="color: #999">结束时间</span
><span style="color: #666; margin-right: 20px">{{ dayjs(zyInfo.endTime).format('MM.DD HH:mm') }}</span>
2024-08-19 08:37:20 +08:00
</a-col>
<a-col :span="24" style="margin-top: 10px">
<div style="display: flex">
<div class="tjfx-line diva" @click="handleDjjgs(zyInfo, '')"
><span class="tjfx-colt">{{ zyInfo.xkrs }}</span
><span class="tjfx-colw"> 总人数</span></div
>
<div class="tjfx-line diva" @click="handleDjjgs(zyInfo, '1')"
><span class="tjfx-colt">{{ zyInfo.ywcrs }}</span
><span class="tjfx-colw"> 已完成人数</span></div
>
<div class="tjfx-line diva" @click="handleDjjgs(zyInfo, '0')"
><span class="tjfx-colt">{{ zyInfo.wwcrs }}</span
><span class="tjfx-colw"> 未完成人数</span></div
>
</div>
</a-col>
2024-10-15 18:21:39 +08:00
<a-col :span="24" style="margin-top: 10px; text-align: right">
<a-switch style="margin-right: 20px" checkedChildren="统计" unCheckedChildren="图表" v-model:checked="twoShowType" />
2024-08-19 08:37:20 +08:00
</a-col>
2024-10-15 18:21:39 +08:00
<a-col :span="23.5" style="margin: 10px 20px" v-if="twoShowType">
2024-08-19 08:37:20 +08:00
<a-collapse accordion expandIconPosition="right">
<a-collapse-panel :key="index" v-for="(item, index) in zyInfo.tmlbList">
<template #header>
2024-08-19 11:32:55 +08:00
<a-row :span="24" style="width: 90%">
2024-11-11 18:33:09 +08:00
<a-col :span="24" class="title2"><div v-html="item.wjTitle"></div></a-col>
2024-10-15 18:21:39 +08:00
<a-col :span="8" style="color: #909399; display: flex; flex-direction: column; text-align: left; font-size: 12px"
><span style="font-weight: bold; font-size: 20px; margin-left: 5px">{{ item.yzd }}</span
>已作答人数</a-col
>
<a-col :span="8" style="color: #1ab394; display: flex; flex-direction: column; text-align: left; font-size: 12px"
><span style="font-weight: bold; font-size: 20px; margin-left: 5px">{{ item.ddrs }}</span
>{{ item.wjType == '8' ? '已批阅人数' : '答对人数' }}</a-col
>
<a-col :span="8" style="color: #f56c6c; display: flex; flex-direction: column; text-align: left; font-size: 12px"
><span style="font-weight: bold; font-size: 20px; margin-left: 5px">{{ item.dcrs }}</span
2024-10-17 11:00:48 +08:00
>{{ item.wjType != '8' ? '答错人数' : '未批阅人数' }}</a-col
2024-10-15 18:21:39 +08:00
>
2024-08-19 08:37:20 +08:00
</a-row>
</template>
<div style="width: 98%; margin: 0 auto" v-if="item.wjType == 3">
<a-card>
<template #extra v-if="zyInfo.atype == 6">
<span class="question-type" style="margin-left: 40px">单选题</span>
<span style="margin-left: 40px"
>题目分值<span class="answer-word"> {{ item.wjScore }}</span> </span
>
</template>
<a-radio-group v-if="!isSmallScreen" v-model:value="item.itemSelected" style="width: 100%" size="default" disabled>
2024-08-19 08:37:20 +08:00
<div style="width: 100%" v-for="(tmxx, index2) in item.wjxWjxxTmxxList" :key="index2">
<a-radio :value="tmxx.itemIndex + ``" style="width: 100%; margin-bottom: 5px">
<span v-html="tmxx.itemTitle" style="font-size: 16px; color: #000"></span>
<span v-if="tmxx.itemSelected == 'true'" style="color: #9e9e9e; margin-left: 30px; font-size: 12px">(正确答案)</span>
<span class="tjfx-xzrs">选择人数{{ tmxx.num }}</span>
</a-radio>
</div>
</a-radio-group>
<a-radio-group v-if="isSmallScreen" v-model:value="item.itemSelected" style="width: 100%" size="default" disabled>
<div v-for="(tmxx, index2) in item.wjxWjxxTmxxList" :key="index2" class="radio-item">
<!-- Radio 按钮和标题 -->
<div style="display: flex; align-items: center;">
<a-radio :value="tmxx.itemIndex + ''">
<span v-html="tmxx.itemTitle" style="font-size: 16px; color: #000;"></span>
</a-radio>
</div>
<!-- 正确答案和选择人数 -->
<div style="display: flex; justify-content: space-between; margin-top: 5px;padding-left:20px;height: 25px;">
<span v-if="tmxx.itemSelected == 'true'" style="color: #9e9e9e; font-size: 12px;">(正确答案)</span>
<span class="tjfx-xzrs" >选择人数{{ tmxx.num }}</span>
</div>
<!-- 分隔线仅在不是最后一个选项时显示 -->
<hr v-if="index2 !== item.wjxWjxxTmxxList.length - 1" class="divider-line"/>
</div>
</a-radio-group>
2024-08-19 08:37:20 +08:00
</a-card>
</div>
<!-- 多选题 -->
<div style="width: 98%; margin: 0 auto" v-else-if="item.wjType == 4">
<a-card>
<template #extra v-if="zyInfo.atype == 6">
<span class="question-type" style="margin-left: 40px">多选题</span>
<span style="margin-left: 40px"
>题目分值 <span class="answer-word">{{ item.wjScore }}</span> </span
>
</template>
<a-checkbox-group v-if="isSmallScreen" v-model:value="item.itemSelected" style="width: 100%" size="default" disabled>
<a-row>
<a-col :span="24" v-for="(tmxx, index2) in item.wjxWjxxTmxxList" :key="index2">
<!-- Checkbox and Title -->
<div style="display: flex; flex-direction: column;">
<a-checkbox :value="tmxx.itemIndex" style="flex: 1 0 auto; width: 100%; margin-bottom: 5px;">
<div style="width: 100%; font-size: 16px; color: #000; word-break: break-all; white-space: normal;">
<span v-html="tmxx.itemTitle"></span>
</div>
</a-checkbox>
<!-- Correct Answer and Selection Count -->
<div style="display: flex; align-items: center; height: 50px;"
:style="{ 'border-bottom': index2 !== item.wjxWjxxTmxxList.length - 1 ? '1px solid #ccc' : 'none' }">
<span v-if="tmxx.itemSelected == 'true'" style="color: #9e9e9e; flex: 1; font-size: 12px;">(正确答案)</span>
<span class="tjfx-xzrs" style="text-align: right; padding-right: 10px; flex: 1;">选择人数{{ tmxx.num }}</span>
</div>
</div>
</a-col>
</a-row>
</a-checkbox-group>
<a-checkbox-group v-if="!isSmallScreen" v-model:value="item.itemSelected" style="width: 100%" size="default" disabled>
2024-08-19 08:37:20 +08:00
<a-row>
<a-col :span="24" v-for="(tmxx, index2) in item.wjxWjxxTmxxList" :key="index2">
<a-checkbox :value="tmxx.itemIndex" style="width: 100%; margin-bottom: 5px">
<span v-html="tmxx.itemTitle" style="width: 80%; font-size: 16px; color: #000"></span>
<span v-if="tmxx.itemSelected == 'true'" style="color: #9e9e9e; margin-left: 30px; font-size: 12px">(正确答案)</span>
<span class="tjfx-xzrs">选择人数{{ tmxx.num }}</span>
</a-checkbox>
</a-col>
</a-row>
</a-checkbox-group>
</a-card>
</div>
<!-- 填空题 -->
<div style="width: 98%; margin: 0 auto" v-else-if="item.wjType == 5 && isSmallScreen">
<a-card>
<!-- 确保正确答案正确人数错误人数各占一行 -->
<div style="text-align: left;">
<!-- 正确答案独占一行 -->
<div v-if="item.wjAnswer" style="color: #9e9e9e; margin-bottom: 4px;">
(正确答案: {{ item.wjAnswer }})
</div>
<!-- 正确人数独占一行 -->
<div style="color: #9e9e9e; margin-bottom: 4px;">
正确人数{{ item.num }}
</div>
<!-- 错误人数独占一行 -->
<div style="color: #9e9e9e; margin-bottom: 4px;">
错误人数{{ item.num2 }}
</div>
</div>
<!-- 题目类型和分值独占一行 -->
<template #extra v-if="zyInfo.atype == 6">
<div style="display: flex;justify-content: space-between;align-items: center;">
<!-- 确保填空题独占一行 -->
<div>
<span class="question-type">填空题</span>
</div>
<!-- 确保题目分值独占一行 -->
<div>
<span style="margin-left: 10px;">题目分值<span class="answer-word">{{ item.wjScore }}</span> </span>
</div>
</div>
</template>
</a-card>
</div>
<div style="width: 98%; margin: 0 auto" v-else-if="item.wjType == 5 && !isSmallScreen">
2024-08-19 08:37:20 +08:00
<a-card>
<template #title>
<span v-if="item.wjAnswer" style="color: #9e9e9e; margin-left: 30px; font-size: 12px">(正确答案:{{ item.wjAnswer }})</span>
<span class="tjfx-xzrs1" style="color: #9e9e9e">正确人数{{ item.num }}</span>
<span class="tjfx-xzrs1" style="color: #9e9e9e">错误人数{{ item.num2 }}</span>
</template>
<template #extra v-if="zyInfo.atype == 6">
<span class="question-type" style="margin-left: 40px">填空题</span>
<span style="margin-left: 40px"
>题目分值<span class="answer-word"> {{ item.wjScore }}</span> </span
>
</template>
</a-card>
</div>
2024-10-15 18:21:39 +08:00
<!-- 文件题 -->
<div style="width: 98%; margin: 0 auto" v-else-if="item.wjType == 8">
<!-- <span style="text-align: left;width: 50%;font-weight: bold;font-size: 18px;padding: 20px;">填空题</span> -->
<!-- <span class="tjfx-zql">正确率15%</span> -->
<a-card>
<template #title v-if="!isSmallScreen">
2024-10-15 18:21:39 +08:00
<j-upload v-model:value="item.picPath" fileType="image" :max-count="1" disabled :buttonVisible="false"></j-upload>
<!-- <span>{{ index + 1 }}</span><span v-html="item.wjTitle" style="white-space: pre-wrap; word-wrap: break-word" /> -->
<!-- <span v-if="item.wjAnswer" style="color: #9e9e9e; margin-left: 30px; font-size: 12px">(正确答案:{{ item.wjAnswer }})</span>
<span class="tjfx-xzrs1" style="color: #9e9e9e">正确人数{{ item.num }}</span>
<span class="tjfx-xzrs1" style="color: #9e9e9e">错误人数{{ item.num2 }}</span> -->
</template>
<j-upload v-if="isSmallScreen" v-model:value="item.picPath" fileType="image" :max-count="1" disabled :buttonVisible="false"></j-upload>
2024-10-15 18:21:39 +08:00
<template #extra v-if="zyInfo.atype == 6">
<span class="question-type" style="margin-left: 40px">文件题</span>
<span style="margin-left: 40px"
>题目分值<span class="answer-word"> {{ item.wjScore }}</span> </span
>
</template>
</a-card>
</div>
2024-08-19 08:37:20 +08:00
<div v-else> 无对应类型 </div>
</a-collapse-panel>
</a-collapse>
</a-col>
<!-- 图表 -->
2024-10-15 18:21:39 +08:00
<a-col :span="23.5" style="margin: 10px 20px" v-if="!twoShowType">
2024-08-19 08:37:20 +08:00
<a-collapse accordion expandIconPosition="right">
<a-collapse-panel :key="index" v-for="(item, index) in zyInfo.tmlbList">
<template #header>
<a-row :span="24" style="width: 100%">
2024-11-11 18:33:09 +08:00
<a-col :span="24" class="title2"><div v-html="item.wjTitle"></div></a-col>
2024-08-19 08:37:20 +08:00
</a-row>
</template>
<!-- 单选题 -->
<div style="width: 98%; margin: 0 auto">
<a-row :span="24">
<a-col :span="24" :lg="{span:12}">
<pie :chartData="getPieData(item)" :option="pieOption" :height="isSmallScreen?'20vh':'300px'" class="char-class" />
2024-08-19 08:37:20 +08:00
</a-col>
<a-col :span="24" :lg="{span:12}">
<BarMulti :chartData="getBarData(item)" :option="multiBarOption" :height="isSmallScreen?'30vh':'300px'" class="char-class"></BarMulti>
2024-08-19 08:37:20 +08:00
</a-col>
</a-row>
</div>
<!-- 多选题 -->
<!-- <div style="width: 98%; margin: 0 auto" v-else-if="item.wjType == 4">
</div> -->
<!-- 填空题 -->
<!-- <div style="width: 98%; margin: 0 auto" v-else-if="item.wjType == 5">
</div> -->
<!-- <div v-else> 无对应类型 </div> -->
</a-collapse-panel>
</a-collapse>
</a-col>
<a-col style="height: 40px"> </a-col>
</a-row>
</a-layout-content>
<!-- 页尾 -->
<footerPage style="margin-top: 10px" />
</a-layout>
</div>
<WjxWjxxTmlbDjjgsModal ref="WjxWjxxTmlbDjjgsModalPage"></WjxWjxxTmlbDjjgsModal>
</div>
</template>
<script lang="ts" name="zyInfo-zyInfo" setup>
import { ref, reactive, onMounted, unref, onBeforeUnmount, onUnmounted, watchEffect } from 'vue';
2024-08-19 08:37:20 +08:00
import { defHttp } from '/@/utils/http/axios';
import { useMessage } from '/@/hooks/web/useMessage';
import { useRouter } from 'vue-router';
import dayjs, { Dayjs } from 'dayjs';
import { Form } from 'ant-design-vue';
import { getValueType } from '/@/utils';
import headerPage from '/@/views/site/common/header.vue';
import footerPage from '/@/views/site/common/footer.vue';
import Pie from '/@/components/chart/Pie.vue';
import BarMulti from '/@/components/chart/BarMulti.vue';
import WjxWjxxTmlbDjjgsModal from '/@/views/kc/wjxWjxx/components/WjxWjxxTmlbDjjgsModal.vue';
2024-10-15 18:21:39 +08:00
import JUpload from '/@/components/Form/src/jeecg/components/JUpload/JUpload.vue';
2024-08-19 08:37:20 +08:00
//当前路由信息
const { currentRoute } = useRouter();
const { query } = unref(currentRoute);
const { rwbh, xqxn, type, teano, cyid } = query; //获取传递参数
const { createConfirm, createMessage } = useMessage();
const zyInfo = ref<any>({});
const WjxWjxxTmlbDjjgsModalPage = ref();
const twoShowType = ref<boolean>(true);
let intervalId: ReturnType<typeof setInterval> | null;
const aaaaa = ref<number>(0);
const multiBarOption = {
title: { text: '答题情况统计', left: 'center' },
};
const pieOption = {
title: { text: '正确率统计', left: 'center' },
};
function getPieData(item) {
2024-10-15 18:21:39 +08:00
console.log('👩', item);
if(item.wjType == 8){
const pieData = [
{ value: parseInt(item.ddrs), name: '已批阅人数' },
{ value: parseInt(item.dcrs), name: '未批阅人数' },
];
return pieData;
}else{
const pieData = [
{ value: parseInt(item.ddrs), name: '答对人数' },
{ value: parseInt(item.dcrs), name: '答错人数' },
];
return pieData;
}
2024-08-19 08:37:20 +08:00
}
function getBarData(item) {
2024-10-15 18:21:39 +08:00
if(item.wjType == 8){
const barMultiData = [
{ value: parseInt(item.yzd), name: '作答人数' },
{ value: parseInt(item.ddrs), name: '已批阅人数' },
{ value: parseInt(item.dcrs), name: '未批阅人数' },
];
return barMultiData;
}else{
const barMultiData = [
{ value: parseInt(item.yzd), name: '作答人数' },
{ value: parseInt(item.ddrs), name: '答对人数' },
{ value: parseInt(item.dcrs), name: '答错人数' },
];
return barMultiData;
}
2024-08-19 08:37:20 +08:00
}
function reloadZy() {
defHttp.get({ url: '/wjxWjxx/wjxWjxx/queryCyjgById', params: { id: cyid } }).then((res) => {
zyInfo.value = res;
});
}
/**
* 学生答卷列表
*/
function handleDjjgs(record: Recordable, flag) {
WjxWjxxTmlbDjjgsModalPage.value.disableSubmit = true;
WjxWjxxTmlbDjjgsModalPage.value.edit(record, flag);
}
onMounted(() => {
reloadZy();
intervalId = setInterval(() => {
// 执行要重复执行的逻辑
reloadZy();
if (zyInfo.value.xkrs == zyInfo.value.ywcrs) {
clear();
}
2024-10-15 18:21:39 +08:00
}, 15000);
2024-08-19 08:37:20 +08:00
});
function clear() {
intervalId && window.clearInterval(intervalId);
}
const isSmallScreen = ref(false);
const checkScreenSize = () => {
isSmallScreen.value = window.innerWidth <= 768; // 根据需要调整断点
};
// 立即执行一次以设置初始值,并在组件卸载前监听窗口大小变化
watchEffect(() => {
checkScreenSize();
const resizeObserver = () => checkScreenSize();
window.addEventListener('resize', resizeObserver);
onUnmounted(() => {
window.removeEventListener('resize', resizeObserver);
});
});
2024-08-19 08:37:20 +08:00
</script>
<style lang="less" scoped>
.title {
line-height: 100px;
font-size: 18px;
}
.title2 {
font-size: 18px;
2024-08-19 11:32:55 +08:00
font-weight: bold;
color: #333;
2024-08-19 08:37:20 +08:00
}
.ant-divider-horizontal {
display: flex;
clear: both;
width: 100%;
min-width: 100%;
margin: 3px 0 5px;
}
.tishi {
width: 100%;
font-size: 12px;
color: #fd8f02;
margin-top: -4px;
background: #fffbf2;
text-align: center;
padding: 6px 0;
}
.cardClass {
min-height: 200px;
}
.sznrClass {
line-height: 40px;
text-align: center;
}
.ant-card {
box-sizing: border-box;
margin: 2px 0;
padding: 0;
color: rgb(0 0 0);
font-size: 14px;
font-variant: tabular-nums;
line-height: 1.5715;
list-style: none;
font-feature-settings: tnum;
position: relative;
border-radius: 5px;
border: 1px solid #dadada;
background: #fff;
}
.ant-card-head {
min-height: 48px;
margin-bottom: -1px;
padding: 0 24px;
color: rgba(0, 0, 0, 0.85);
font-weight: 500;
font-size: 16px;
background: transparent;
border-bottom: 1px solid #dadada;
border-radius: 2px 2px 0 0;
}
.ellipsis {
overflow: hidden; /* 确保超出容器的内容被裁剪 */
white-space: nowrap; /* 确保文本在一行内显示 */
text-overflow: ellipsis; /* 超出部分显示省略号 */
}
.ellip-title {
display: flex;
justify-content: space-between;
}
.elli-title {
font-size: 16px;
font-weight: bold;
}
.ellip-word {
font-size: 14px;
color: #666666;
}
.zuanqu:hover {
cursor: pointer;
color: #18a689;
}
.data-suggest {
display: flex;
flex-direction: column;
text-align: center;
width: 25%;
margin-right: 3px;
padding: 8px 3px;
border-radius: 5px;
background: #f7f7f7;
margin-top: 10px;
}
.data-suggest span:nth-child(1) {
font-size: 16px;
font-weight: bold;
}
.data-suggest span:nth-child(2) {
font-size: 12px;
}
.work-img {
width: 100%;
display: flex;
justify-content: center;
margin-top: 80px;
margin-bottom: 30px;
}
.work-img-img {
width: 180px;
height: 139px;
}
.buttonClass {
background: #1ab394;
font-weight: 600;
color: #fff;
border-radius: 3px;
border: none;
}
.mar-right20 {
margin-right: 14px;
}
.button-zhta {
color: #666666;
cursor: pointer;
}
.button-zhta:hover {
cursor: pointer;
color: #18a689;
}
.diva {
cursor: pointer;
color: #18a689;
}
.sear-distance {
padding: 0 10px;
}
.ant-form-item {
box-sizing: border-box;
margin: 10px 0;
padding: 0;
color: rgba(0, 0, 0, 0.85);
font-size: 14px;
font-variant: tabular-nums;
line-height: 1.5715;
list-style: none;
font-feature-settings: tnum;
/* margin-bottom: 24px; */
vertical-align: top;
}
.bled-countenance {
color: #333333;
}
.bled-countenance2 {
color: #999999;
font-size: 12px;
}
.region {
margin: 5px 10px;
padding-bottom: 20px;
background: #fff;
border-radius: 5px;
}
.region-title {
font-size: 16px;
color: #029c88;
padding: 8px 20px;
border-left: 5px solid #029c88;
margin: 10px;
border-radius: 5px;
background: #fff;
}
.tjfx-col {
font-size: 12px;
padding: 8px 20px;
line-height: 25px;
}
.tjfx-col-title {
font-size: 16px;
padding: 8px 20px;
line-height: 25px;
font-weight: bold;
}
.tjfx-line {
2024-10-15 18:21:39 +08:00
width: 33%;
2024-08-19 08:37:20 +08:00
text-align: center;
display: flex;
flex-direction: column;
background: #f7f7f7;
border-radius: 5px;
margin: 0 15px;
padding: 8px 0;
}
.tjfx-colt {
font-size: 22px;
font-weight: bold;
color: #1ab394;
}
.tjfx-colw {
font-size: 14px;
color: #666;
}
.tjfx-title {
width: 90%;
float: left;
}
.tjfx-type {
width: 10%;
float: left;
}
.tjfx-xzrs {
margin-left: 30px;
font-size: 12px;
position: absolute;
right: 15px;
}
@media (max-width: 768px) { /* 根据需要调整这个宽度 */
.tjfx-xzrs {
font-size: 12px;
}
}
.divider-line {
border: none;
height: 1px;
background-color: #e0e0e0; /* 淡灰色 */
margin: 10px 0; /* 上下间距 */
}
2024-08-19 08:37:20 +08:00
.tjfx-xzrs1 {
margin-left: 30px;
font-size: 12px;
}
.tjfx-zql {
text-align: right;
width: 50%;
font-size: 16px;
padding: 20px;
}
.question-type {
background: #eaf9f6;
color: #1ab394;
padding: 0 5px;
border-radius: 3px;
border: 1px solid #1ab394;
}
.answer-word {
color: #ff8710;
font-weight: bold;
}
#siteMain {
// font-size: ;
// height: 100%;
background: #f3f3f4;
#maxSite {
//最大宽度
max-width: 1170px;
//居中
margin: 0 auto;
.rowGutter {
margin-top: 1rem;
margin-bottom: 1rem;
}
.ant-layout-header {
color: #fff;
background: #1ab394;
}
.ant-layout-footer {
line-height: 1.5;
background: #fff;
}
.ant-layout-sider {
color: #fff;
background: #3ba0e9;
}
.ant-layout-content {
color: #000;
background: #f3f3f4;
}
.dictBox :deep(.ant-select) {
width: 100%;
}
}
}
@media (max-width: 768px) {
.char-class{
width:70vw;
}
}
@media (min-width: 769px) {
.char-class{
width:300px;
}
}
2024-08-19 08:37:20 +08:00
</style>