
File name
Commit message
Commit date
File name
Commit message
Commit date
File name
Commit message
Commit date
File name
Commit message
Commit date
File name
Commit message
Commit date
2024-11-19
<template>
<div>
<!-- <Side_t></Side_t> -->
<div style="padding: 15px 60px 120px 60px">
<div class="flex justify-between align-center">
<div class="logo mb25"><img src="../../../resources/img/logo2.png" alt="" /></div>
<Header></Header>
</div>
<div class="main-wrap flex justify-between">
<div class="gd-2">
<div class="mb30">
<div>
<img src="../../../resources/img/img16_s.png" alt="" />
<div class="mt10" style="width: 100%">
<p class="name mb10">{{ studentInfo.studentName }}</p>
<p class="mb5">
{{ studentInfo.institutionName }} {{ studentInfo.grade }}학년
{{ studentInfo.className }}
</p>
<!-- <progress-bar :progress="progress"></progress-bar> -->
<div class="problem-box mt25">
<p style="font-weight: bold">
지금까지 푼 총 문제 수 :
<span style="color: #9528b7; font-size: 16px; font-weight: bold"
>{{ studentInfo.totalProblemsSolved }}개</span
>
</p>
</div>
</div>
</div>
<hr />
<div class="history-box">
<p class="title2 mb25">최근 학습 히스토리</p>
<ul class="flex justify-between">
<li v-for="historyItem in studentInfo.history" :key="historyItem.unitId">
[{{ historyItem.bookName }}] {{ historyItem.unitName }}
</li>
</ul>
</div>
<hr />
<div class="title-box flex justify-between mb20">
<p class="name">{{ studentInfo.studentName }}학생 랭킹</p>
</div>
<div class="mypage mb30">
<div class="flex-column" style="gap: 20px">
<div class="textbook book-red">
<div class="text">
<p class="title1" style="color: #fff">포토북 랭킹</p>
</div>
<div class="box">
<P class="title2 mt10"
>현재 {{ stdCount }}명 중 <em class="red">{{ photo_rank }}등</em>입니다.</P
>
</div>
</div>
<div class="textbook">
<div class="text">
<p class="title1" style="color: #fff">진도율 랭킹</p>
</div>
<div class="box">
<P class="title2 mt10"
>현재 {{ stdCount }}명 중
<em class="yellow">{{ problem_rank }}등</em>입니다.</P
>
</div>
</div>
<div class="textbook book-blue">
<div class="text">
<p class="title1" style="color: #fff">점수 랭킹</p>
</div>
<div class="box">
<P class="title2 mt10"
>현재 {{ stdCount }}명 중 <em class="blue">{{ score_rank }}등</em>입니다.</P
>
</div>
</div>
<div class="textbook book-navy">
<div class="text">
<p class="title1" style="color: #fff">학습시간 랭킹</p>
</div>
<div class="box">
<P class="title2 mt10"
>현재 {{ stdCount }}명 중 <em class="navy">{{ time_rank }}등</em>입니다.</P
>
</div>
</div>
</div>
</div>
<hr />
<div>
<div class="title-box flex justify-between mb20">
<p class="title">사진첩</p>
</div>
<div class="photobook">
<div class="flex justify-between">
<div class="box" style="gap: 5px">
<div><img src="../../../resources/img/img198_12p.png" alt="" /></div>
</div>
<div class="text mt10">
<p class="title1 mb10">{{ studentInfo.studentName }}의 사진첩</p>
<button
@click="goToPage('PhotoBook_p')"
type="button"
title="글쓰기"
class="new-btn"
>
바로가기
</button>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="gd-9 flex-column" style="flex: 1">
<div class="title-box flex justify-between mb40">
<p class="title">전체 진행률</p>
</div>
<div class="flex">
<div class="wrap" style="flex: 1">
<p class="name">학습 현황</p>
<div class="flex justify-center">
<Dounutchart />
</div>
<div class="textbox">
<p class="title2">오늘의 학습현황</p>
<!-- 안전하게 진도율을 소수점 한자리 수까지 표시 -->
<p class="name">
{{
donutChartData.clearUnitNum && donutChartData.totalScheduleUnitNum
? (
(donutChartData.clearUnitNum / donutChartData.totalScheduleUnitNum) *
100
).toFixed(1)
: 0
}}
%
</p>
</div>
<p class="title2">학습시간</p>
<p class="name">학습시간 n시간</p>
</div>
<div class="wrap" style="flex: 1">
<p class="name">이해/표현 점수</p>
<div class="flex justify-center mt50">
<ColumnLineChart />
</div>
</div>
</div>
<div class="wrap" style="flex: 2">
<p class="name">교재별 진행률</p>
<div class="flex justify-center">
<StackedBarChart />
</div>
</div>
<div class="flex">
<div class="wrap" style="flex: 1">
<p class="name">오늘의 학습 일정</p>
<div
class="scheduleBox mt20"
style="gap: 20px"
v-for="(schedule, index) in schedules"
:key="index"
>
<div class="flex justify-between align-center" style="gap: 70px">
<div><img src="../../../resources/img/img217_22s.png" alt="" /></div>
<div
class="wrap cs-pt"
:class="{ 'cs-pt-clicked': isClicked }"
@click="toggleClicked"
style="width: 100%"
>
<div class="text-lf flex justify-between align-center">
<div>
<div class="flex align-center mb10" style="gap: 10px">
<p class="title2">
<em class="gray-bd">{{ schedule.schdl_unit }}교시</em>
</p>
<p class="title1">{{ schedule.schedule_time }}</p>
</div>
<div class="title-box mb10">
<span class="title">{{ schedule.unit_nm }}</span>
</div>
<p class="title2">{{ schedule.book_nm }}</p>
</div>
<div class="">
<img src="../../../resources/img/img214_19s.png" alt="" />
</div>
</div>
</div>
</div>
</div>
</div>
<div class="flex-column" style="flex: 1">
<div class="wrap">
<p class="name">교재별 오답률</p>
<div class="flex justify-center">
<Barchart />
</div>
</div>
<div class="wrap">
<p class="name">문제 카테고리별 세부 점수</p>
<div class="flex justify-center">
<CategoryBarChart />
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</template>
<script>
import Header from '../../layout/Header.vue';
import Menu from '../../layout/Menu.vue';
import Side_t from '../../layout/Side_t.vue';
import ProgressBar from '../../component/ProgressBar.vue';
import StackedBarChart from './StackedBarChart.vue';
import Barchart from './Barchart.vue';
// import Bubblechart from './Bubblechart.vue';
import CategoryBarChart from './CategoryBarChart.vue';
import Dounutchart from './Dounutchart.vue';
import ColumnLineChart from './ColumnLineChart.vue';
import axios from 'axios';
export default {
data() {
return {
stdCount: 0,
photo_rank: 0,
problem_rank: 0,
score_rank: 0,
time_rank: 0,
progress: 20,
donutChartData: {},
currentDate: '2024-10-25',
studentInfo: {
studentName: '',
institutionName: '',
grade: '',
className: '',
studentQuestion: '',
history: [],
},
currentStdId: 'USID_000000000000002',
schedules: [],
timeList: [
{ label: '1교시', time: '08:00 ~ 09:00', value: '1' },
{ label: '2교시', time: '09:00 ~ 10:00', value: '2' },
{ label: '3교시', time: '10:00 ~ 11:00', value: '3' },
{ label: '4교시', time: '11:00 ~ 12:00', value: '4' },
{ label: '5교시', time: '13:00 ~ 14:00', value: '5' },
{ label: '6교시', time: '14:00 ~ 15:00', value: '6' },
],
};
},
methods: {
goToPage(page) {
this.$router.push({ name: page });
},
classStdCount: function () {
const vm = this;
axios({
url: '/userclass/classStdCountByUserId.json',
method: 'post',
headers: {
'Content-Type': 'application/json; charset=UTF-8',
},
data: {
userId: 'USID_000000000000002', // 로그인한 학생의 userId
},
})
.then(function (response) {
console.log('classStdCount - response : ', response.data);
vm.stdCount = response.data;
})
.catch(function (error) {
console.log('classStdCount - error : ', error);
alert('반 학생 수 조회에 오류가 발생했습니다.');
});
},
photoRankByLikeData: function () {
const vm = this;
axios({
url: '/photo/photoRankByLikeData.json',
method: 'post',
headers: {
'Content-Type': 'application/json; charset=UTF-8',
},
data: {
sclsId: '1',
stdId: '1',
},
})
.then(function (response) {
console.log('Photo Rank - response : ', response.data);
vm.photo_rank = response.data;
})
.catch(function (error) {
console.log('Photo Rank - error : ', error);
alert('학생 사진 랭킹 조회에 오류가 발생했습니다.');
});
},
getUserRankByScore: function () {
const vm = this;
axios({
url: '/userclass/getUserRankByScore.json',
method: 'post',
headers: {
'Content-Type': 'application/json; charset=UTF-8',
},
data: {
userId: 'USID_000000000000002', // 로그인한 학생의 userId
},
})
.then(function (response) {
console.log('User Rank - response : ', response.data);
vm.score_rank = response.data;
})
.catch(function (error) {
console.log('User Rank - error : ', error);
alert('점수 랭킹 조회에 오류가 발생했습니다.');
});
},
getUserRankByStudyTime: function () {
const vm = this;
axios({
url: '/userclass/getUserRankByStudyTime.json',
method: 'post',
headers: {
'Content-Type': 'application/json; charset=UTF-8',
},
data: {
userId: '1', // 로그인한 학생의 userId
},
})
.then(function (response) {
console.log('User Rank - response : ', response.data);
vm.time_rank = response.data;
})
.catch(function (error) {
console.log('User Rank - error : ', error);
alert('학습시간 랭킹 조회에 오류가 발생했습니다.');
});
},
problemRankByProblemData: function () {
const vm = this;
axios({
url: '/problemLog/problemRankByProblemData.json',
method: 'post',
headers: {
'Content-Type': 'application/json; charset=UTF-8',
},
data: {
sclsId: '1',
stdId: '2',
},
})
.then(function (response) {
console.log('Problem Rank - response : ', response.data);
vm.problem_rank = response.data;
})
.catch(function (error) {
console.log('Problem Rank - error : ', error);
alert('학생 문제 랭킹 조회에 오류가 발생했습니다.');
});
},
// 학생 데이터 가져오기
fetchStudentInfo() {
axios
.post('/studentInfo/getInfo.json', { userId: this.currentStdId })
.then((response) => {
console.log(response.data);
this.studentInfo = response.data;
})
.catch((error) => {
console.error('학생 정보 가져오기 실패:', error);
});
},
// 현재 날짜의 학생 학습률 데이터 가져오기
getStdProgressData() {
const vm = this;
axios
.post('/dashboard/stdProgressData.json', {
std_id: vm.currentStdId,
current_date: vm.currentDate,
})
.then((response) => {
vm.donutChartData = response.data;
console.log(vm.donutChartData);
})
.catch((error) => {
console.error('오늘의 학생 학습 현황 데이터를 가져오는 중 오류 발생:', error);
});
},
// 현재학생의 학습 스케줄 가져오기
fetchSchedules() {
axios
.post(
'/schedule/selectSchedule.json',
{ stdId: '2' },
{
headers: {
'Content-Type': 'application/json; charset=UTF-8',
},
}
)
.then((response) => {
this.schedules = response.data.map((schedule) => {
const matchingTime = this.timeList.find((time) => time.value === schedule.schdl_unit);
return {
...schedule,
schedule_time: matchingTime ? matchingTime.time : '시간 정보 없음',
};
});
console.log(this.schedules);
})
.catch((error) => {
console.error('fetchUnits - error:', error);
alert('단원 목록을 불러오는 중 오류가 발생했습니다.');
});
},
},
watch: {},
computed: {},
components: {
Header: Header,
Menu: Menu,
// Footer:Footer,
Side_t: Side_t,
ProgressBar,
StackedBarChart: StackedBarChart,
Barchart: Barchart,
// Bubblechart: Bubblechart,
CategoryBarChart,
Dounutchart: Dounutchart,
ColumnLineChart: ColumnLineChart,
},
mounted() {
this.getStdProgressData();
this.fetchStudentInfo();
this.classStdCount();
this.photoRankByLikeData();
this.getUserRankByScore();
this.problemRankByProblemData();
this.getUserRankByStudyTime();
this.fetchSchedules();
},
};
</script>
<style scoped>
.main-wrap {
margin-top: 20px;
position: static;
width: 100%;
height: 100%;
}
.history-box {
background-color: white;
padding: 30px 20px;
border: 1px solid #c6c6c6;
border-radius: 10px;
}
.history-box li {
background-color: #eaedf4;
border-radius: 10px;
font-size: 18px;
list-style-type: none;
padding: 10px;
width: 100%;
}
.problem-box {
display: flex;
align-items: center;
justify-content: center;
border: 2px solid #6327b9;
background-color: #f0eaf8;
border-radius: 8px;
padding: 10px 10px;
}
.scheduleBox {
display: flex;
flex-direction: column;
}
</style>