Merge branch 'master' of https://gitea.xn--7p0a.site/2312072104/dm
This commit is contained in:
commit
29c15e93d3
|
@ -1,4 +1,4 @@
|
||||||
import './trainmanage.css'
|
import './Trainmanage.css'
|
||||||
import { Link } from 'react-router-dom';
|
import { Link } from 'react-router-dom';
|
||||||
// import React, { useEffect, useState } from 'react';
|
// import React, { useEffect, useState } from 'react';
|
||||||
// import axios from 'axios';
|
// import axios from 'axios';
|
||||||
|
|
|
@ -1,135 +1,177 @@
|
||||||
import { useParams } from 'react-router-dom';
|
import { useParams } from 'react-router-dom';
|
||||||
import { Link } from 'react-router-dom';
|
import { Link } from 'react-router-dom';
|
||||||
import React, { useEffect, useState } from 'react';
|
import React, { useEffect, useState } from 'react';
|
||||||
import { BarChart, Bar, XAxis, YAxis, CartesianGrid, Tooltip } from 'recharts';
|
import { BarChart, Bar, XAxis, YAxis, CartesianGrid, Tooltip } from 'recharts';
|
||||||
import axios from 'axios';
|
import axios from 'axios';
|
||||||
import './classid.css'
|
import './classid.css'
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
function TeacherPage() {
|
function TeacherPage() {
|
||||||
const click=()=>{
|
const [selectedSubject, setSelectedSubject] = useState();
|
||||||
console.log(TestScore);
|
const [ID,setID]=useState(null)
|
||||||
}
|
const[TestScore,setTestScore]=useState([])
|
||||||
const teacher_ID=localStorage.getItem('islogin')
|
const { key } = useParams();
|
||||||
if(teacher_ID==null){
|
const [isclick,setisclick]=useState(false)
|
||||||
alert('登录过期,请重新登录')
|
const [classdata,setClassData]=useState([])
|
||||||
window.location.href='http://36.138.114.105:30294/'
|
const [studentScores, setStudentScores] = useState([])
|
||||||
}
|
const [name,setname]=useState('')
|
||||||
const { key } = useParams();
|
|
||||||
const [isclick,setisclick]=useState(false)
|
const click=()=>{
|
||||||
//学生表格
|
console.log(selectedSubject);
|
||||||
const [classdata,setClassData]=useState([])
|
console.log(ID);
|
||||||
const class_succeed = async () => {
|
console.log(studentScores);
|
||||||
try{
|
|
||||||
const class_scr=await axios.post('/api/teacher/find_student',{key})
|
|
||||||
const class_data=class_scr.data
|
|
||||||
setClassData(class_data[1])
|
|
||||||
setisclick(true)
|
|
||||||
}catch(error){
|
|
||||||
alert(error)
|
|
||||||
}
|
}
|
||||||
}
|
const teacher_ID=localStorage.getItem('islogin')
|
||||||
useState(()=>{
|
if(teacher_ID==null){
|
||||||
class_succeed();
|
alert('登录过期,请重新登录')
|
||||||
},[])
|
window.location.href='http://36.138.114.105:30294/'
|
||||||
|
|
||||||
//柱形图
|
|
||||||
const [studentScores, setStudentScores] = useState([]);
|
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
class_succeed().then(() => {
|
|
||||||
const scores = classdata.map(student => ({
|
|
||||||
name: 11.26, // 学生姓名
|
|
||||||
score:10, // 学生分数
|
|
||||||
}));
|
|
||||||
setStudentScores(scores);
|
|
||||||
});
|
|
||||||
}, [isclick]);
|
|
||||||
|
|
||||||
function formatDate(dateString) {
|
|
||||||
// 将日期字符串转换为 Date 对象
|
|
||||||
const date = new Date(dateString);
|
|
||||||
// 获取年份、月份和日期
|
|
||||||
const year = date.getFullYear();
|
|
||||||
const monthIndex = date.getMonth();
|
|
||||||
const day = date.getDate();
|
|
||||||
|
|
||||||
// 构建格式化后的日期字符串
|
|
||||||
const formattedDate = `${year}-${(monthIndex + 1).toString().padStart(2, '0')}-${day.toString().padStart(2, '0')}`;
|
|
||||||
return formattedDate;
|
|
||||||
}
|
|
||||||
const[TestScore,setTestScore]=useState()
|
|
||||||
const Find_details=async (ID)=>{
|
|
||||||
try{
|
|
||||||
const Find_details_Src=await axios.post('api/Find_details',{
|
|
||||||
ID
|
|
||||||
})
|
|
||||||
setTestScore(Find_details_Src.data)
|
|
||||||
}catch{
|
|
||||||
alert('Find_details出错')
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
//学生表格
|
||||||
|
|
||||||
|
const class_succeed = async () => {
|
||||||
|
try{
|
||||||
|
const class_scr=await axios.post('/api/teacher/find_student',{key})
|
||||||
|
const class_data=class_scr.data
|
||||||
|
setClassData(class_data[1])
|
||||||
|
setisclick(true)
|
||||||
|
}catch(error){
|
||||||
|
alert(error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
useState(()=>{
|
||||||
|
class_succeed();
|
||||||
|
},[])
|
||||||
|
|
||||||
return(
|
useEffect(() => {
|
||||||
<div className='body-right-classId'>
|
class_succeed().then(() => {
|
||||||
<div id='body-right-bottom'>
|
const scores = [];
|
||||||
<h3>班级信息</h3>
|
// 遍历 TestScore 对象的每个值
|
||||||
<div id='body-right-bottom-left'>
|
for (const studentId in TestScore) {
|
||||||
<div id='body-right-bottom-left-nav'>
|
// 如果当前学生的信息数组没有被跳过,则对其做进一步处理
|
||||||
<p style={{ display: 'flex', justifyContent: 'space-between' }}>
|
if (TestScore.hasOwnProperty(studentId)) {
|
||||||
<span style={{ flex: 1 }}>班级</span>
|
const studentInfo = TestScore[studentId];
|
||||||
<span style={{ flex: 1 }}>姓名</span>
|
// 检查当前学生的信息数组是否符合特定的科目要求
|
||||||
<span style={{ flex: 1 }}>学号</span>
|
if (studentInfo[2] === selectedSubject) {
|
||||||
<span style={{ flex: 1 }}>性别</span>
|
// 只有当学生信息数组的第3个元素(科目)等于"Chinese"时,才添加到 scores 数组中
|
||||||
<span style={{ flex: 1 }}>联系电话</span>
|
scores.push({
|
||||||
<span style={{ flex: 1 }}>出生日期</span>
|
name: studentInfo[3], // 假设姓名总是位于数组的第4个位置
|
||||||
<span style={{ flex: 1 }}>查看详情</span>
|
score: studentInfo[5], // 假设分数总是位于数组的第6个位置
|
||||||
</p>
|
});
|
||||||
|
// 如果 scores 数组已经有三个或更多项目,则移除数组的第一个项目
|
||||||
|
if (scores.length > 3) {
|
||||||
|
scores.shift();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setStudentScores(scores);
|
||||||
|
});
|
||||||
|
}, [selectedSubject]);
|
||||||
|
|
||||||
|
function formatDate(dateString) {
|
||||||
|
// 将日期字符串转换为 Date 对象
|
||||||
|
const date = new Date(dateString);
|
||||||
|
// 获取年份、月份和日期
|
||||||
|
const year = date.getFullYear();
|
||||||
|
const monthIndex = date.getMonth();
|
||||||
|
const day = date.getDate();
|
||||||
|
|
||||||
|
// 构建格式化后的日期字符串
|
||||||
|
const formattedDate = `${year}-${(monthIndex + 1).toString().padStart(2, '0')}-${day.toString().padStart(2, '0')}`;
|
||||||
|
return formattedDate;
|
||||||
|
}
|
||||||
|
|
||||||
|
const Find_details= async ()=>{
|
||||||
|
if(ID!==null){
|
||||||
|
try{
|
||||||
|
const Find_details_Src = await axios.post('/api/teacher/Find_details',{
|
||||||
|
ID
|
||||||
|
})
|
||||||
|
setTestScore(Find_details_Src.data['TestScore'])
|
||||||
|
setStudentScores([])
|
||||||
|
setSelectedSubject()
|
||||||
|
}catch{
|
||||||
|
alert('Find_details')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
useEffect(()=>{
|
||||||
|
Find_details()
|
||||||
|
const sltvalue=document.getElementById('selectvalue')
|
||||||
|
sltvalue.value=''
|
||||||
|
},[ID])
|
||||||
|
|
||||||
|
function handleSubjectChange(event) {
|
||||||
|
setSelectedSubject(event.target.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleClick = (item) => {
|
||||||
|
setID(classdata[item][1]);
|
||||||
|
setname(classdata[item][0]);
|
||||||
|
};
|
||||||
|
|
||||||
|
return(
|
||||||
|
<div className='body-right-classId'>
|
||||||
|
<div id='body-right-bottom'>
|
||||||
|
<h3>班级信息</h3>
|
||||||
|
<div id='body-right-bottom-left'>
|
||||||
|
<div id='body-right-bottom-left-nav'>
|
||||||
|
<p style={{ display: 'flex', justifyContent: 'space-between' }}>
|
||||||
|
<span style={{ flex: 1 }}>班级</span>
|
||||||
|
<span style={{ flex: 1 }}>姓名</span>
|
||||||
|
<span style={{ flex: 1 }}>学号</span>
|
||||||
|
<span style={{ flex: 1 }}>性别</span>
|
||||||
|
<span style={{ flex: 1 }}>联系电话</span>
|
||||||
|
<span style={{ flex: 1 }}>出生日期</span>
|
||||||
|
<span style={{ flex: 1 }}>查看详情</span>
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<div id='body-right-student-box'>
|
||||||
|
<table>
|
||||||
|
<tbody>
|
||||||
|
{Object.keys(classdata).map((item)=>(
|
||||||
|
<tr key={item}>
|
||||||
|
<td className='box-content'>{classdata[item][2]}</td>
|
||||||
|
<td className='box-content'>{classdata[item][0]}</td>
|
||||||
|
<td className='box-content'>{classdata[item][1]}</td>
|
||||||
|
<td className='box-content'>{classdata[item][3]}</td>
|
||||||
|
<td className='box-content'>{classdata[item][5]}</td>
|
||||||
|
<td className='box-content'>{formatDate(classdata[item][4])}</td>
|
||||||
|
<td className='box-content'><button onClick={(e)=>handleClick(item)} style={{border:'none'}}>查看详情</button></td>
|
||||||
|
</tr>
|
||||||
|
))}
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div id='body-right-student-box'>
|
</div>
|
||||||
<table>
|
<div className='body-test-score'>
|
||||||
<tbody>
|
<h3>成绩</h3>
|
||||||
{Object.keys(classdata).map((item)=>(
|
<div className='body-test-score-bar'>
|
||||||
<tr key={item}>
|
{name&&<div className='studentName'>已选中{name}</div>}
|
||||||
<td className='box-content'>{classdata[item][2]}</td>
|
<button onClick={click}>测试</button>
|
||||||
<td className='box-content'>{classdata[item][0]}</td>
|
<select onChange={handleSubjectChange} id='selectvalue'>
|
||||||
<td className='box-content'>{classdata[item][1]}</td>
|
<option value="">请选择科目</option>
|
||||||
<td className='box-content'>{classdata[item][3]}</td>
|
<option value="Chinese">语文</option>
|
||||||
<td className='box-content'>{classdata[item][5]}</td>
|
<option value="Math">数学</option>
|
||||||
<td className='box-content'>{formatDate(classdata[item][4])}</td>
|
<option value="English">英语</option>
|
||||||
<td className='box-content'><button onClick={()=>Find_details(classdata[item][1])} style={{border:'none'}}>查看详情</button></td>
|
<option value="Train">实训</option>
|
||||||
</tr>
|
</select>
|
||||||
))}
|
<div className='table-bar'>
|
||||||
</tbody>
|
<BarChart width={600} height={350} data={studentScores} barSize={80} className='bar' >
|
||||||
</table>
|
<CartesianGrid strokeDasharray="3 3" />
|
||||||
|
<XAxis dataKey="name" />
|
||||||
|
<YAxis dataKey="score"/>
|
||||||
|
<Tooltip />
|
||||||
|
<Bar dataKey="score" fill="#ffeed4" />
|
||||||
|
</BarChart>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className='body-test-score'>
|
)
|
||||||
<h3>成绩</h3>
|
}
|
||||||
<div className='body-test-score-bar'>
|
export default TeacherPage;
|
||||||
<div className='studentName'>名字</div>
|
|
||||||
<button onClick={click}>测试</button>
|
|
||||||
<select>
|
|
||||||
<option value="">请选择科目</option>
|
|
||||||
<option value="china">语文</option>
|
|
||||||
<option value="math">数学</option>
|
|
||||||
<option value="english">英语</option>
|
|
||||||
<option value="test">实训</option>
|
|
||||||
</select>
|
|
||||||
<div className='table-bar'>
|
|
||||||
<BarChart width={600} height={350} data={studentScores} barSize={90} className='bar' >
|
|
||||||
<CartesianGrid strokeDasharray="3 3" />
|
|
||||||
<XAxis dataKey="name" />
|
|
||||||
<YAxis dataKey="score"/>
|
|
||||||
<Tooltip />
|
|
||||||
<Bar dataKey="score" fill="#ffeed4" />
|
|
||||||
</BarChart>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
export default TeacherPage;
|
|
|
@ -102,7 +102,5 @@
|
||||||
.studentName{
|
.studentName{
|
||||||
margin-top: 20px;
|
margin-top: 20px;
|
||||||
font-size: 18px;
|
font-size: 18px;
|
||||||
width: 72px;
|
|
||||||
margin-left: 50px;
|
margin-left: 50px;
|
||||||
border: 1px solid black;
|
|
||||||
}
|
}
|
|
@ -2,4 +2,5 @@ function List_pods(){
|
||||||
return(
|
return(
|
||||||
<div></div>
|
<div></div>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
export default List_pods
|
|
@ -23,8 +23,8 @@ import ClassID from '../TeacherPages/classlistpages/classId';
|
||||||
import ManageTest from '../TeacherPages/TestManage/ManageTest';
|
import ManageTest from '../TeacherPages/TestManage/ManageTest';
|
||||||
import SendTest from '../TeacherPages/TestManage/SendTest';
|
import SendTest from '../TeacherPages/TestManage/SendTest';
|
||||||
import Marking from '../TeacherPages/MarkingPages/Marking';
|
import Marking from '../TeacherPages/MarkingPages/Marking';
|
||||||
import SendTrain from '../TeacherPages/TrainManage/SendTrain';
|
import SendTrain from '../TeacherPages/Trainmanage/SendTrain';
|
||||||
import TrainManage from '../TeacherPages/TrainManage/trainmanage';
|
import TrainManage from '../TeacherPages/Trainmanage/Trainmanage';
|
||||||
import StudentLink from '../TeacherPages/MarkingPages/StudentLink';
|
import StudentLink from '../TeacherPages/MarkingPages/StudentLink';
|
||||||
|
|
||||||
// 定义一个组件来包裹除了特定页面(exam)外的所有页面使其有导航
|
// 定义一个组件来包裹除了特定页面(exam)外的所有页面使其有导航
|
||||||
|
@ -72,7 +72,7 @@ function App() {
|
||||||
{/* 页面使用单独的布局,不包含HeaderNav和HeaderNavTeacher */}
|
{/* 页面使用单独的布局,不包含HeaderNav和HeaderNavTeacher */}
|
||||||
<Route path="exam/:examId" element={<Exam />} />{/* 练习-考试页面 */}
|
<Route path="exam/:examId" element={<Exam />} />{/* 练习-考试页面 */}
|
||||||
<Route path='/teacher/sendtest' element={<SendTest />}/> {/* 考试管理-发布试卷 */}
|
<Route path='/teacher/sendtest' element={<SendTest />}/> {/* 考试管理-发布试卷 */}
|
||||||
<Route path='/teacher/SendTrain' element={<SendTrain/>}/> {/* 实训管理-发布实训 */}
|
<Route path='/teacher/SendTrain' element={<SendTrain/>}/> {/*实训管理-发布实训*/}
|
||||||
<Route path='operation1/:operateID' element={<Operation1/>}/> {/* 实训页面1 */}
|
<Route path='operation1/:operateID' element={<Operation1/>}/> {/* 实训页面1 */}
|
||||||
<Route path='operation2/:operateID' element={<Operation2/>}/> {/* 实训页面2 */}
|
<Route path='operation2/:operateID' element={<Operation2/>}/> {/* 实训页面2 */}
|
||||||
<Route path='/refresh' element={<Refresh/>}/>
|
<Route path='/refresh' element={<Refresh/>}/>
|
||||||
|
|
|
@ -231,10 +231,13 @@ def SendTrainTest():
|
||||||
return '发布成功'
|
return '发布成功'
|
||||||
|
|
||||||
|
|
||||||
@app.route('/api/Find_details',methods=["POST"])
|
@app.route('/api/teacher/Find_details',methods=["POST"])
|
||||||
def Find_details():
|
def Find_details():
|
||||||
id=request.json['student_ID']
|
data=request.json
|
||||||
return Find_details(id)
|
ID=data['ID']
|
||||||
|
result=Find_details_Func(ID)
|
||||||
|
print(result)
|
||||||
|
return jsonify({'TestScore':result})
|
||||||
|
|
||||||
|
|
||||||
@app.route('/')
|
@app.route('/')
|
||||||
|
|
|
@ -269,7 +269,7 @@ def SendTrainTestFunc(TrainChoice,TrainCompletion,TrainJudge,Hour,Min,StopTime,C
|
||||||
# return dic_last_three # 返回一个新字典,该字典仅包含排序后的最后三个键及其对应的值
|
# return dic_last_three # 返回一个新字典,该字典仅包含排序后的最后三个键及其对应的值
|
||||||
|
|
||||||
|
|
||||||
def Find_details(ID):
|
def Find_details_Func(ID):
|
||||||
dic = {}
|
dic = {}
|
||||||
cursor = db.cursor()
|
cursor = db.cursor()
|
||||||
cursor.execute(f"SELECT * FROM STUDENT_TEST WHERE STUDENT_ID=? AND TF='true' ", (ID))
|
cursor.execute(f"SELECT * FROM STUDENT_TEST WHERE STUDENT_ID=? AND TF='true' ", (ID))
|
||||||
|
|
Loading…
Reference in New Issue