Compare commits

...

16 Commits

Author SHA1 Message Date
yangws 06cb96c7bc Merge pull request 'fix:地址修改;' (#374) from yangws into main
Reviewed-on: #374
2024-10-28 17:14:47 +08:00
小杨 8784c0cfe3 fix:地址修改; 2024-10-28 17:14:14 +08:00
yangws 9e13e3dfb5 Merge pull request 'fix:作业统计相关问题以及优化;' (#373) from yangws into main
Reviewed-on: #373
2024-10-28 17:12:52 +08:00
小杨 c8aae6f408 fix:作业统计相关问题以及优化; 2024-10-28 17:12:32 +08:00
baigl 13f7398d79 Merge pull request 'baigl' (#372) from baigl into main
Reviewed-on: #372
2024-10-28 14:15:11 +08:00
白了个白 6ef29f2b5a Merge branch 'main' of http://27.128.240.72:3000/zhuhao/AIx_Smarttalk into baigl 2024-10-28 14:14:20 +08:00
白了个白 5cf7d737d6 批阅:习题学生答案背景颜色修改-对绿错红 2024-10-28 14:13:56 +08:00
baigl 346b07e47a Merge pull request '作业批阅:习题训练类型 新增客观题自动批阅逻辑更改' (#371) from baigl into main
Reviewed-on: #371
2024-10-28 10:50:14 +08:00
白了个白 743d8e05d3 作业批阅:习题训练类型 新增客观题自动批阅逻辑更改 2024-10-28 10:48:51 +08:00
yangws 7c9b2755f2 Merge pull request 'fix:价值透析数据修改;' (#370) from yangws into main
Reviewed-on: #370
2024-10-25 16:41:15 +08:00
小杨 25acd398ff fix:价值透析数据修改; 2024-10-25 16:40:53 +08:00
yangws fe078e7ce5 Merge pull request 'fix:价值透析数据修改;' (#369) from yangws into main
Reviewed-on: #369
2024-10-25 16:37:28 +08:00
小杨 eaaba2b5e8 fix:价值透析数据修改; 2024-10-25 16:37:06 +08:00
zhengdegang 4816a4565b Merge pull request 'zdg' (#368) from zdg into main
Reviewed-on: #368
2024-10-25 15:29:56 +08:00
zdg 8b55ebffa5 ppt点赞优化 2024-10-25 15:28:54 +08:00
zdg 9674c68d11 修复-侧边工具 2024-10-25 15:05:25 +08:00
9 changed files with 267 additions and 196 deletions

View File

@ -75,12 +75,12 @@ let studentList = ref([]) // 学生数据
// -
const initData = () => {
console.log('xxx', props)
// window.test = activeCourse
studentList.value = props.activeData.studentList || []
const activeWorkFeedList = props.activeData.workFeedList || []
const quizlist = props.activeData.quizlist || []
const timeArr = groupByField(props.activeData.workFeedList,'entpcourseworkid')
console.log(quizlist,'quizlist');
//
let data = quizlist.map(o => {
//
@ -90,14 +90,9 @@ const initData = () => {
let rightIds = [] //
let hasAnswers= [] //
let timeAnalyse = [] //
// let subjectCourese = [] //
const quizFeedList = activeWorkFeedList.filter(f => f.entpcourseworkid == o.id) //
//
timeArr.forEach((item,index) => {
const arr = item.reduce((acc, cur) => {
return acc + (cur.timelength ? Number(cur.timelength) : 0);
},0)
timeAnalyse.push(arr)
})
let children = []
const allStudents = [];
if (o.worktype == '单选题') { // '',''
@ -108,6 +103,11 @@ const initData = () => {
// id
const studentIds = quizFeedList.filter(f => f.feedcontent==v&&f.finishtimelength!='0').map(f => f.studentid)||[];
accSum += studentIds.length;
//
timeAnalyse = quizFeedList.reduce((acc, cur) => {
return acc + (cur.timelength ? Number(cur.timelength) : 0);
},0)
if (isOk) {
activeIds.push(...studentIds)
}
@ -135,6 +135,10 @@ const initData = () => {
if (studentIds.length>0) {
allStudents.push(...studentIds);
}
//
timeAnalyse = quizFeedList.reduce((acc, cur) => {
return acc + (cur.timelength ? Number(cur.timelength) : 0);
},0)
if(isOk) {
activeIds=[...new Set(activeIds.concat(studentIds))] //
}
@ -153,6 +157,10 @@ const initData = () => {
activeIds=[...new Set(activeIds.concat(studentIds))] //
hasAnswers=[...new Set(hasAnswers.concat(studentIds))]
accSum = activeIds.length
//
timeAnalyse = quizFeedList.reduce((acc, cur) => {
return acc + (cur.timelength ? Number(cur.timelength) : 0);
},0)
return { def, code, txt, isOk:true, studentIds }
})
} else if (o.worktype == '判断题') { //
@ -194,6 +202,10 @@ const initData = () => {
accSum += studentIds.length;
if(isOk) activeIds.push(...studentIds)
hasAnswers.push(...studentIds)
//
timeAnalyse = quizFeedList.reduce((acc, cur) => {
return acc + (cur.timelength ? Number(cur.timelength) : 0);
},0)
return { def: v, code: v, isOk, studentIds }
})
} else { //
@ -203,6 +215,10 @@ const initData = () => {
activeIds=[...new Set(activeIds.concat(studentIds))] //
hasAnswers=[...new Set(hasAnswers.concat(studentIds))]
accSum = activeIds.length
//
timeAnalyse = quizFeedList.reduce((acc, cur) => {
return acc + (cur.timelength ? Number(cur.timelength) : 0);
},0)
children = [{ def, code, isOk:true, studentIds }]
}
@ -222,7 +238,7 @@ const initData = () => {
}
// def: type active: points: , accSum
return { def: o, id: o.id, type: o.worktype, active: [], points, accSum, rightSum, children,hasAnswers,timeAnalyse }
return { def: o, id: o.id, type: o.worktype, active: [], points, accSum, rightSum, children,hasAnswers,timeAnalyse,score:o.score }
})
if (data.length === 0) return
useOverview.getAllData([...data])

View File

@ -24,6 +24,7 @@ const dataList = ref([
//
const hasStudents = ref([])
//
function getColor(name) {
const colorMap = {
@ -104,7 +105,18 @@ const showEcharts = () => {
}
//
watch(() => useOverview.tableList, () => {
//
const subType = useOverview.allData.map(item => item.type)
const objectiveQuestion = ['单选题','多选题','判断题']
if( !subType.every(item => objectiveQuestion.includes(item)) ){
hasStudents.value = useOverview.tableList.filter(item => {
if(item.rating > 0 && useOverview.allData[0].hasAnswers.includes(item.studentid)){
return item
}
})
}else{
hasStudents.value = useOverview.tableList.filter(item => useOverview.allData[0].hasAnswers.includes(item.studentid)).map(item => item);
}
showEcharts();
nextTick(() => {
initChart();

View File

@ -81,7 +81,18 @@ const showStudents = (index) => {
})
}
watch(() => useOverview.tableList, () => {
//
const subType = useOverview.allData.map(item => item.type)
const objectiveQuestion = ['单选题','多选题','判断题']
if( !subType.every(item => objectiveQuestion.includes(item)) ){
hasStudents.value = useOverview.tableList.filter(item => {
if(item.rating > 0 && useOverview.allData[0].hasAnswers.includes(item.studentid)){
return item
}
})
}else{
hasStudents.value = useOverview.tableList.filter(item => useOverview.allData[0].hasAnswers.includes(item.studentid)).map(item => item);
}
showStudents(0)
},{deep: true})
</script>

View File

@ -20,82 +20,80 @@
<script setup>
import {ref, watch} from 'vue'
import overviewStore from '@/store/modules/overview'
import {listEntpcoursework} from '@/api/education/entpCourseWork'
const useOverview = overviewStore()
const tableData = ref([])
//id
const ids = ref('')
//
const allScore = ref(0)
//
const konwledge = ref([])
const hasStudents = ref([])
//
const allScore = ref([])
//
const getKonwledge = () => {
useOverview.tableList.forEach(item => {
const getScoreRate = []
//
const ledges = []
hasStudents.value.forEach((item,index) => {
//
if(item.knowledgePoint){
konwledge.value.push({...JSON.parse(item.knowledgePoint),...{scoingRate:Number(item.scoingRate),point:item.point,allPoint:allScore.value}})
const title = JSON.parse(item.knowledgePoint)
//
if(!ledges.includes(title.id)){
ledges.push(title.id)
// 0
konwledge.value.push({title:title.title,allPoint:allScore.value,id:title.id})
}
//
if(useOverview.allData[0].hasAnswers.includes(item.studentid))
getScoreRate.push({rate:item.scoingRate,id:title.id})
}
})
tableData.value = getTableList(konwledge.value)
tableData.value = tableData.value.map(item => {
return{
//
konwledge.value.forEach(item => {
let sunRate = 0
let num = 0
if(getScoreRate.length === 0) return
getScoreRate.forEach(item2 => {
if(item.id === item2.id){
sunRate += extractedNumber(item2.rate)
num ++
}
})
const scoreRate = sunRate / num
tableData.value.push({
scoingRate:scoreRate.toFixed(2),
...item,
allPoint: allScore.value
}
point:(item.allPoint * scoreRate / 100).toFixed(2)
})
})
console.log(tableData.value,'tableData.value')
}
//
const getScore = async () => {
const scoreId = useOverview.tableList[0].entpcourseworklist
const fixedJsonString = `[${scoreId}]`;
const objects = JSON.parse(fixedJsonString);
const id = objects.map(obj => obj.id);
ids.value = id.join(',')
const res = await listEntpcoursework({ids: ids.value, pageSize: 500})
if(res.code === 200){
allScore.value = res.rows.reduce((acc, cur) => acc + cur.workScore, 0);
getKonwledge()
}
//
const extractedNumber = (score) => {
const match = score.match(/\d+/);
return match ? parseInt(match[0], 10) : null;
}
//tableList
const getTableList = (data) => {
const result = [];
data.forEach(item => {
const existingItem = result.find(i => i.id === item.id);
if (existingItem) {
// pointscoingRate
existingItem.pointTotal += parseInt(item.point);
existingItem.scoingRateTotal += parseFloat(item.scoingRate);
existingItem.count++;
} else {
//
result.push({
id: item.id,
title: item.title,
pointTotal: item.point,
scoingRateTotal: parseFloat(item.scoingRate),
count: 1
});
}
});
//
result.forEach(item => {
item.point = Math.round(item.pointTotal / item.count);
// item.scoingRate = Math.round((item.scoingRateTotal / item.count) * 100) / 100;
item.scoingRate = Math.round((item.point / allScore.value) * 100);
delete item.pointTotal;
delete item.scoingRateTotal;
delete item.count;
});
return result;
}
watch(() => useOverview.tableList,() => {
console.log(useOverview.tableList,'useOverview.tableList')
getScore()
//
const subType = useOverview.allData.map(item => item.type)
const objectiveQuestion = ['单选题','多选题','判断题']
if( !subType.every(item => objectiveQuestion.includes(item)) ){
hasStudents.value = useOverview.tableList.filter(item => {
if(item.rating > 0 && useOverview.allData[0].hasAnswers.includes(item.studentid)){
return item
}
})
}else{
hasStudents.value = useOverview.tableList.filter(item => useOverview.allData[0].hasAnswers.includes(item.studentid)).map(item => item);
}
//
allScore.value = useOverview.allData.reduce((acc, cur) => {
return acc + Number(cur.score)
},0)
getKonwledge()
})
</script>

View File

@ -9,14 +9,17 @@ import * as echarts from 'echarts';
import {ref, nextTick, watch} from 'vue'
import overviewStore from '@/store/modules/overview'
const useOverview = overviewStore()
const useOverview = overviewStore();
//
const chartRef = ref(null);
//
const expectedDuration = ref([]);
//
function initChart() {
const myChart = echarts.init(chartRef.value);
//
let option = {
tooltip: {
@ -24,16 +27,17 @@ function initChart() {
axisPointer: {
type: "shadow", // 线'line' | 'shadow'
},
formatter: function(parms) {
let str =
parms[0].axisValue +
"</br>" +
parms[0].marker +
"平均用时:" +
parms[0].value + 's'
formatter: function (parms) {
let str = "";
parms.forEach(param => {
if (param.seriesType === 'bar') {
str += param.axisValue + "</br>" + param.marker + "平均用时:" + param.value + 's' + "</br>";
} else if (param.seriesType === 'line') {
str += param.marker + "预计用时:" + param.value + 's';
}
});
return str;
},
},
textStyle: {
color: "#333",
@ -63,7 +67,7 @@ function initChart() {
color: "#000",
},
},
name:'题目编号'
name: '题目编号'
},
yAxis: {
type: "value",
@ -73,7 +77,7 @@ function initChart() {
color: "#B5B5B5",
},
},
name:'平均时长',
name: '平均时长',
splitLine: {
lineStyle: {
// 使
@ -84,7 +88,8 @@ function initChart() {
},
axisLabel: {},
},
series: [{
series: [
{
data: getYValue(),
stack: "zs",
type: "bar",
@ -98,45 +103,61 @@ function initChart() {
y2: 1,
type: "linear",
global: false,
colorStops: [{
offset: 0,
color: "#5EA1FF",
},
{
offset: 1,
color: "#90BEFF",
},
colorStops: [
{ offset: 0, color: "#5EA1FF" },
{ offset: 1, color: "#90BEFF" },
],
},
},
label: {
show: true,
position: 'top',
formatter: '{c}s',
color: '#333',
},
},
//线
{
data: expectedDuration.value,
type: "line",
smooth: true,
symbol: 'circle',
symbolSize: 8,
lineStyle: {
color: '#FF7F50',
width: 2,
},
itemStyle: {
color: '#FF7F50',
},
},
],
};
myChart.setOption(option);
}
//
//
const getYValue = () => {
const arr = [...useOverview.allData[0].timeAnalyse]
const num = useOverview.allData[0].hasAnswers.length
const arr = useOverview.allData.map(item => item.timeAnalyse)
const num = useOverview.allData[0].hasAnswers.length;
if (arr.length === 0) return [];
return arr.map(item => (item ? (item / num).toFixed(2) : 0));
};
return arr.map(item => {
return item ? (item / num).toFixed(2) : 0
})
}
//
//
const getXValue = () => {
return useOverview.allData.map(item => item.id)
}
return useOverview.allData.map((item, index) => `${index + 1}`);
};
watch(() => useOverview.tableList, () => {
expectedDuration.value = useOverview.tableList.map(item => (Number(item.timelength) * 60 / useOverview.allData.length).toFixed(2));
watch(() => useOverview.tableList,() => {
//
//
nextTick(() => {
initChart();
})
})
});
});
</script>
<style scoped>

View File

@ -90,7 +90,7 @@
<span>学生答案
<span
v-if="stuItem.feedcontent !=''"
style="background-color: red; color: white; padding: 0 5px; border-radius: 5px;"
:style="{backgroundColor: `${formatWorkAnswer(quItem) == formatFeedContent(stuItem, quItem)? '#0ed116' : 'red'}`,color: 'white', padding: '0 5px', borderRadius: '5px'}"
v-html="formatFeedContent(stuItem, quItem)"
>
</span>

View File

@ -390,17 +390,29 @@ const getClassWorkStudentList = (rowId) => {
tableRadio.value = '1'
tableRadio.num0 = classWorkAnalysis.classworkdata.length - tableRadio.list.length
tableRadio.num1 = tableRadio.list.length
tableRadio.list = tableRadio.list.map((item) => {
return {
...item,
teacherRating : checkWorkType(item)
}
})
//
teacherCriticism();
})
.catch(() => {
loading_dt_table.value = false
})
}
/**
* 自动批阅判断
* 已交 作业类型为习题训练
*/
const teacherCriticism = ()=>{
// list
if(tableRadio.value == '1'&& classWorkAnalysis.worktype == '习题训练'){
//
tableRadio.list = tableRadio.list.map((item) => {
return {
...item,
teacherRating : item.teacherRating || checkWorkType(item)
}
})
}
}
const checkWorkType = (item) => {
//
const subType = classWorkActiveData.quizlist.map(item => item.worktype)
@ -408,7 +420,7 @@ const checkWorkType = (item) => {
let rating = 0
//
if(subType.every(item => objectiveQuestion.includes(item))){
//
// scoingRate
const score = extractedNumber(item.scoingRate)
if(0<=score && score<=59){
rating = 5
@ -551,6 +563,8 @@ const tableRadioChange = (e) => {
tableRadio.value = '1';
tableRadio.num0 = classWorkAnalysis.classworkdata.length - tableRadio.list.length;
tableRadio.num1 = tableRadio.list.length;
//
teacherCriticism();
}else if(e=='0'){
tableRadio.list = classWorkAnalysis.classworkdata.filter(item => item.finishtimelength == '0')
tableRadio.value = '0';

View File

@ -73,9 +73,8 @@ const list = computed(() => props.data.map((o,i) => {
}))
onMounted(() => {
posBtnAll = btnRef.value.getBoundingClientRect()
hPost.value = posBtnAll.height
curNode = sessionStore.get('subject.curNode')
hPost.value = Math.round(posBtnAll.height)
curNode = sessionStore?.get?.('subject.curNode')
})
// === ===
//
@ -97,7 +96,7 @@ const clickHandel = (o, e) => {
isVisible.value = !isColse //
activeObj.value = o
const nodeH = parseInt(node.height / 2) //
topPos.value = parseInt(node.top) - posBtnAll.top + nodeH
topPos.value = Math.round(parseInt(node.top) - posBtnAll.top + nodeH)
}
emit('change', o)
}
@ -149,8 +148,8 @@ const closeActive = () =>{
--top: 30px;
--height: 40vh;
position: fixed;
inset: 50% 75px auto auto;
transform: translateY(-50%);
inset: 0 75px auto auto;
// transform: translateY(-50%);
background-color: #121212;
padding: 10px;
border-radius: 4px;

View File

@ -1,6 +1,6 @@
<template>
<div v-if="props.test">
<el-button type="primary" @click="trigger" v-tap:trigger="">点赞</el-button>
<el-button type="primary" @click="trigger(1)" v-tap:trigger="[1,'']">点赞</el-button>
<el-button type="primary" @click="trigger(2, '学生A')" v-tap:trigger="[2,'学生A']">疑惑</el-button>
</div>
<!-- 温度计-模式 -->
@ -258,11 +258,11 @@ defineExpose({ trigger })
min-width: 15px;
// height: 500px;
&.like{
background-image: linear-gradient(to top, #fef0f0, #f56c6c);
background-image: linear-gradient(to top, #d2f0cb, #2f9e44);
// animation: striped-flow 5s linear infinite;
}
&.doubt{
background-image: linear-gradient(to top, #fdf6ec, #e6a23c);
background-image: linear-gradient(to top, #ebc6c6, #ff0000);
}
}
}