From ca9a92cfc2f2bd8c724020ee5e46094633eb80a5 Mon Sep 17 00:00:00 2001
From: 黄何裕 <1053952480@qq.com>
Date: 星期五, 12 七月 2024 17:39:45 +0800
Subject: [PATCH] 处理冲突
---
src/components/NormalHeader/index.vue | 4
src/views/personal-center/index.vue | 195 +++++++++++++++++
src/views/home/components/user-panel/index.vue | 228 ++++++++++----------
components.d.ts | 4
src/api/modules/personalCenter.js | 9
auto-imports.d.ts | 2
vite.config.js | 2
src/router/index.js | 5
src/views/exam/index.vue | 175 ++++++++++-----
9 files changed, 439 insertions(+), 185 deletions(-)
diff --git a/auto-imports.d.ts b/auto-imports.d.ts
index 1d89ee8..78813d8 100644
--- a/auto-imports.d.ts
+++ b/auto-imports.d.ts
@@ -5,5 +5,5 @@
// Generated by unplugin-auto-import
export {}
declare global {
-
+ const ElMessage: typeof import('element-plus/es')['ElMessage']
}
diff --git a/components.d.ts b/components.d.ts
index a89ff70..1f66d7d 100644
--- a/components.d.ts
+++ b/components.d.ts
@@ -7,12 +7,14 @@
/* prettier-ignore */
declare module 'vue' {
export interface GlobalComponents {
+ ElAvatar: typeof import('element-plus/es')['ElAvatar']
ElButton: typeof import('element-plus/es')['ElButton']
ElCard: typeof import('element-plus/es')['ElCard']
ElCol: typeof import('element-plus/es')['ElCol']
ElCollapse: typeof import('element-plus/es')['ElCollapse']
ElCollapseItem: typeof import('element-plus/es')['ElCollapseItem']
ElCountdown: typeof import('element-plus/es')['ElCountdown']
+ ElDatePicker: typeof import('element-plus/es')['ElDatePicker']
ElDialog: typeof import('element-plus/es')['ElDialog']
ElDropdown: typeof import('element-plus/es')['ElDropdown']
ElDropdownItem: typeof import('element-plus/es')['ElDropdownItem']
@@ -32,6 +34,8 @@
ElSlider: typeof import('element-plus/es')['ElSlider']
ElTable: typeof import('element-plus/es')['ElTable']
ElTableColumn: typeof import('element-plus/es')['ElTableColumn']
+ ElTabPane: typeof import('element-plus/es')['ElTabPane']
+ ElTabs: typeof import('element-plus/es')['ElTabs']
ElTag: typeof import('element-plus/es')['ElTag']
ExamAudio: typeof import('./src/components/ExamAudio/index.vue')['default']
ExamInfo: typeof import('./src/components/ExamInfo/index.vue')['default']
diff --git a/src/api/modules/personalCenter.js b/src/api/modules/personalCenter.js
new file mode 100644
index 0000000..6380f6e
--- /dev/null
+++ b/src/api/modules/personalCenter.js
@@ -0,0 +1,9 @@
+import service from "@/api";
+
+export const uploadImg = (fromData) => {
+ return service.post("/api/student/upload/image", fromData, {
+ headers: {
+ "Content-Type": "multipart/form-data",
+ },
+ });
+};
diff --git a/src/components/NormalHeader/index.vue b/src/components/NormalHeader/index.vue
index c70f50e..dd22149 100644
--- a/src/components/NormalHeader/index.vue
+++ b/src/components/NormalHeader/index.vue
@@ -9,8 +9,8 @@
<div class="user-container flex items-center">
<div class="avatar-container w-12 h-12 rounded-full overflow-hidden mr-3">
- <div class="avatar-content" v-if="userInfo.imagePath"">
- <img :src="userInfo.imagePath" class="avatar-img" alt="">
+ <div class="avatar-content" v-if="userInfo.imagePath">
+ <img :src="'/api/files/'+userInfo.imagePath" class="avatar-img" alt="">
</div>
<div class="avatar-content" :style="{ backgroundColor: getColor }">
<div class="name text-xl font-bold text-white">{{ getFirstName }}</div>
diff --git a/src/router/index.js b/src/router/index.js
index 24bd96d..a327d8e 100644
--- a/src/router/index.js
+++ b/src/router/index.js
@@ -66,6 +66,11 @@
path: '/folder',
component: () => import('@/views/folder/index.vue'),
},
+ //涓汉涓績
+ {
+ path: '/personal-center',
+ component: () => import('@/views/personal-center/index.vue'),
+ }
];
const router = createRouter({
diff --git a/src/views/exam/index.vue b/src/views/exam/index.vue
index bd858ed..dbbf30c 100644
--- a/src/views/exam/index.vue
+++ b/src/views/exam/index.vue
@@ -1,5 +1,7 @@
<template>
- <div class="exam-container w-screen h-screen bg-slate-50 relative overflow-hidden">
+ <div
+ class="exam-container w-screen h-screen bg-slate-50 relative overflow-hidden"
+ >
<div class="top-bg bg-blue-500"></div>
<div class="exam-content">
<div class="exam-wrapper container mx-auto h-full flex flex-col">
@@ -24,8 +26,10 @@
<!-- 绛旈鍗″尯 -->
<div class="answer-wrapper answer-left mr-8 shadow-xl p-4 box-border">
<div class="wrapper h-full flex flex-col items-center">
- <div class="title-wrapper w-full flex justify-between items-center mb-5">
- <div class="title text-xl font-semibold ">绛旈鍗�</div>
+ <div
+ class="title-wrapper w-full flex justify-between items-center mb-5"
+ >
+ <div class="title text-xl font-semibold">绛旈鍗�</div>
<AnswerTag></AnswerTag>
</div>
@@ -40,9 +44,13 @@
</div>
<div class="submit-wrapper">
- <el-button type="primary" class="submit-button" @click="submitExamHandle">鎻愪氦璇曞嵎</el-button>
+ <el-button
+ type="primary"
+ class="submit-button"
+ @click="submitExamHandle"
+ >鎻愪氦璇曞嵎</el-button
+ >
</div>
-
</div>
</div>
@@ -50,15 +58,20 @@
<div class="answer-wrapper answer-right grow shadow-xl p-4">
<div class="wrapper h-full flex flex-col">
<div class="title-wrapper w-full flex mb-5">
- <div class="title text-xl font-semibold ">{{ examType[currentType] }} ({{
- examStore.getActiveQuestion.questionScore }}鍒�)
+ <div class="title text-xl font-semibold">
+ {{ examType[currentType] }} ({{
+ examStore.getActiveQuestion.questionScore
+ }}鍒�)
</div>
</div>
<div class="main-wrapper w-full grow relative my-5">
<div class="main-content absolute top-0 bottom-0 w-full">
<Transition appear name="fade-transform" mode="out-in">
- <component :is="typeComponent[currentType]" :key="currentIndex"></component>
+ <component
+ :is="typeComponent[currentType]"
+ :key="currentIndex"
+ ></component>
</Transition>
</div>
</div>
@@ -66,10 +79,17 @@
<div class="tool-wrapper flex justify-end">
<div class="button-container flex items-center">
<div class="button-item">
- <el-button class="tool-button" @click="prevQuestion">涓婁竴棰�</el-button>
+ <el-button class="tool-button" @click="prevQuestion"
+ >涓婁竴棰�</el-button
+ >
</div>
<div class="button-item">
- <el-button class="tool-button" type="primary" @click="nextQuestion">涓嬩竴棰�</el-button>
+ <el-button
+ class="tool-button"
+ type="primary"
+ @click="nextQuestion"
+ >涓嬩竴棰�</el-button
+ >
</div>
</div>
</div>
@@ -78,7 +98,6 @@
</div>
</div>
</div>
-
<!-- 閫�鍑鸿�冭瘯鎻愮ず寮圭獥 -->
<el-dialog v-model="quitDialog" title="娉ㄦ剰" width="500">
@@ -89,9 +108,7 @@
<template #footer>
<div class="dialog-footer">
<el-button @click="quitDialog = false">缁х画浣滅瓟</el-button>
- <el-button type="danger" @click="confirmQuit">
- 纭畾閫�鍑�
- </el-button>
+ <el-button type="danger" @click="confirmQuit"> 纭畾閫�鍑� </el-button>
</div>
</template>
</el-dialog>
@@ -113,45 +130,50 @@
</el-dialog>
<!-- 鑰冭瘯鏃堕棿寮圭獥 -->
- <el-dialog v-model="timeDialog" align-center width="500" :close-on-click-modal="false"
- :close-on-press-escape="false" :show-close="false">
+ <el-dialog
+ v-model="timeDialog"
+ align-center
+ width="500"
+ :close-on-click-modal="false"
+ :close-on-press-escape="false"
+ :show-close="false"
+ >
<div class="dialog-container flex flex-col items-center">
<div class="icon-container">
<el-icon :size="50" color="#3680fa">
<Timer />
</el-icon>
</div>
- <div class="dialog-info">
- 鑰冭瘯缁撴潫锛岀郴缁熻嚜鍔ㄦ敹鍗蜂腑.......
- </div>
+ <div class="dialog-info">鑰冭瘯缁撴潫锛岀郴缁熻嚜鍔ㄦ敹鍗蜂腑.......</div>
</div>
</el-dialog>
</div>
</template>
<script setup>
-import { ref, watchEffect, watch, onMounted } from 'vue';
-import { storeToRefs } from 'pinia';
-import { Close, Timer } from '@element-plus/icons-vue';
-import AnswerTag from './components/answer-tag/index.vue';
-import AnswerProgress from './components/answer-progress/index.vue';
-import AnswerSheet from './components/answer-sheet/index.vue';
-import AnswerTime from './components/answer-time/index.vue';
+import { ref, watchEffect, watch, onMounted ,onUnmounted} from "vue";
+import { storeToRefs } from "pinia";
+import { Close, Timer } from "@element-plus/icons-vue";
+import AnswerTag from "./components/answer-tag/index.vue";
+import AnswerProgress from "./components/answer-progress/index.vue";
+import AnswerSheet from "./components/answer-sheet/index.vue";
+import AnswerTime from "./components/answer-time/index.vue";
-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 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 { useExamStore, useUserStore } from '@/store/index.js';
-import { useRouter } from 'vue-router';
+import { useExamStore, useUserStore } from "@/store/index.js";
+import { useRouter } from "vue-router";
-import { submitExam } from '@/api/modules/exam.js';
-import useWebScoket from '@/hooks/useWebScoket.js';
+import { submitExam } from "@/api/modules/exam.js";
+import useWebScoket from "@/hooks/useWebScoket.js";
+import { ElMessage, ElMessageBox } from "element-plus";
const router = useRouter();
@@ -159,7 +181,8 @@
const userStore = useUserStore();
const { userInfo } = storeToRefs(userStore);
-const { currentType, currentIndex, examDetail, examType, examInfo } = storeToRefs(examStore);
+const { currentType, currentIndex, examDetail, examType, examInfo } =
+ storeToRefs(examStore);
const typeComponent = {
1: AnswerSingle,
@@ -181,11 +204,11 @@
// heartBeatData: 'ping'
// });
-const { status, message, error, connect, disconnect, sendMessage } = useWebScoket({
- url: '//192.168.3.64:8000/websocket/' + userInfo.value.id,
- heartBeatData: 'ping'
-});
-
+const { status, message, error, connect, disconnect, sendMessage } =
+ useWebScoket({
+ url: "//192.168.3.64:8000/websocket/" + userInfo.value.id,
+ heartBeatData: "ping",
+ });
// 涓婁竴棰�
const prevQuestion = () => {
@@ -220,19 +243,18 @@
currentType.value = typeQuestion.questionType;
currentIndex.value = typeQuestion.questionList.length - 1;
}
-
} else if (currentIndex.value < 0) {
tempIndex--;
if (examDetail.value[tempIndex]) {
currentType.value = examDetail.value[tempIndex].questionType;
- currentIndex.value = examDetail.value[tempIndex].questionList.length - 1;
+ currentIndex.value =
+ examDetail.value[tempIndex].questionList.length - 1;
} else {
currentType.value = typeQuestion.questionType;
currentIndex.value = 0;
}
}
}
-
};
// 閫�鍑鸿�冭瘯
@@ -262,18 +284,20 @@
const timeOut = () => {
const temp = {
...examInfo.value,
- titleList: examDetail.value
+ titleList: examDetail.value,
};
timeDialog.value = true;
resetAllDialog();
disconnect();
- submitExam(temp).then(res => {
- returnBack();
- }).catch(() => {
- returnBack();
- });
+ submitExam(temp)
+ .then((res) => {
+ returnBack();
+ })
+ .catch(() => {
+ returnBack();
+ });
};
const returnBack = () => {
@@ -284,30 +308,55 @@
watchEffect(() => {
let progress = 0;
- examDetail.value.forEach(item => {
- item.questionList.forEach(question => {
- if (question.answer || (Array.isArray(question.answerList) && question.answerList.length)) {
+ examDetail.value.forEach((item) => {
+ item.questionList.forEach((question) => {
+ if (
+ question.answer ||
+ (Array.isArray(question.answerList) && question.answerList.length)
+ ) {
progress += 1;
}
});
});
examStore.setProgress(progress);
});
-const answerTime = ref()
-watch(() => message.value, (msg) => {
- if(msg.commend=="delayed"){
- answerTime.value.addTime(msg.data.addTimeM)
- }else if(msg.commend=="forceSubmit"){
- confirmSubmit()
+const answerTime = ref();
+watch(
+ () => message.value,
+ (msg) => {
+ if (msg.commend == "delayed") {
+ answerTime.value.addTime(msg.data.addTimeM);
+ } else if (msg.commend == "forceSubmit") {
+ confirmSubmit();
+ }
}
-});
-
+);
+// document.addEventListener('blur', function() {
+// console.log('椤甸潰澶卞幓鐒︾偣');
+// });
+const warningNum = ref(0)
+const handleBlur = () => {
+ if (document.visibilityState === "visible") {
+ } else if (document.visibilityState === "hidden") {
+ ElMessageBox.alert("鑰冭瘯杩囩▼涓鍕跨寮�鑰冭瘯椤甸潰锛佽鍛婁笁娆″皢寮哄埗鏀跺嵎", "璀﹀憡", {
+ confirmButtonText: "纭畾",
+ });
+ warningNum.value++
+ if (warningNum.value==3) {
+ timeOut();
+ }
+ }
+};
// -----------------------------------鐢熷懡鍛ㄦ湡
onMounted(() => {
// 杩炴帴webscoket
connect();
+ document.addEventListener("visibilitychange", handleBlur);
});
+onUnmounted(()=>{
+ document.removeEventListener("visibilitychange", handleBlur);
+})
</script>
<style lang="scss" scoped>
diff --git a/src/views/home/components/user-panel/index.vue b/src/views/home/components/user-panel/index.vue
index f6b415c..ed05489 100644
--- a/src/views/home/components/user-panel/index.vue
+++ b/src/views/home/components/user-panel/index.vue
@@ -1,73 +1,62 @@
<template>
- <div class="user-panel max-w-sm min-w-96 h-fit">
- <el-card class="card">
- <div class="panel-content flex flex-col items-center">
- <!-- 瀛︾敓淇℃伅 -->
- <el-dropdown>
- <div
- class="avatar-container w-40 h-40 rounded-full overflow-hidden el-dropdown-link"
- @click="stateClick()"
- >
- <div
- class="avatar-content"
- v-if="userInfo.imagePath"
- >
- <img
- :src="userInfo.imagePath"
- class="avatar-img"
- alt=""
- />
- </div>
- <div
- class="avatar-content"
- :style="{ backgroundColor: getColor }"
- v-else
- >
- <div class="name text-5xl font-bold text-white">
- {{ getFirstName }}
- </div>
- </div>
- </div>
- <template #dropdown>
- <el-dropdown-menu>
- <el-dropdown-item>淇敼瀵嗙爜</el-dropdown-item>
- <el-dropdown-item>涓汉涓績</el-dropdown-item>
- <el-dropdown-item @click="quit()"
- >閫�鍑虹櫥褰�</el-dropdown-item
- >
- </el-dropdown-menu>
- </template>
- </el-dropdown>
-
- <div class="name-container text-lg font-bold mt-5 mb-2">
- {{ userInfo.realName }}
- </div>
-
- <div class="department-container text-base mb-10">
- {{ userInfo.userName }}
- </div>
- <!-- 瀛︾敓閫夐」 -->
- <div class="tool-container grid grid-cols-3 gap-10">
- <div
- class="tool-item text-center cursor-pointer"
- v-for="item in toolList"
- @click="toolClick(item)"
- >
- <div class="tool-icon mb-1">
- <img
- :src="item.iconPath"
- class="width-img"
- alt=""
- />
- </div>
- <div class="tool-title">
- {{ item.title }}
- </div>
- </div>
- </div>
+ <div class="user-panel max-w-sm min-w-96 h-fit">
+ <el-card class="card">
+ <div class="panel-content flex flex-col items-center">
+ <!-- 瀛︾敓淇℃伅 -->
+ <el-dropdown>
+ <div
+ class="avatar-container w-40 h-40 rounded-full overflow-hidden el-dropdown-link"
+ @click="stateClick()"
+ >
+ <div class="avatar-content" v-if="userInfo.imagePath">
+ <img :src="'/api/files/'+userInfo.imagePath" class="avatar-img" alt="" />
</div>
- </el-card>
- </div>
+ <div
+ class="avatar-content"
+ :style="{ backgroundColor: getColor }"
+ v-else
+ >
+ <div class="name text-5xl font-bold text-white">
+ {{ getFirstName }}
+ </div>
+ </div>
+ </div>
+ <template #dropdown>
+ <el-dropdown-menu>
+ <el-dropdown-item>淇敼瀵嗙爜</el-dropdown-item>
+ <el-dropdown-item @click="goPersonalCenter()"
+ >涓汉涓績</el-dropdown-item
+ >
+ <el-dropdown-item @click="quit()">閫�鍑虹櫥褰�</el-dropdown-item>
+ </el-dropdown-menu>
+ </template>
+ </el-dropdown>
+
+ <div class="name-container text-lg font-bold mt-5 mb-2">
+ {{ userInfo.realName }}
+ </div>
+
+ <div class="department-container text-base mb-10">
+ {{ userInfo.userName }}
+ </div>
+ <!-- 瀛︾敓閫夐」 -->
+ <div class="tool-container grid grid-cols-3 gap-10">
+ <div
+ class="tool-item text-center cursor-pointer"
+ v-for="item in toolList"
+ @click="toolClick(item)"
+ >
+ <div class="tool-icon mb-1">
+ <img :src="item.iconPath" class="width-img" alt="" />
+ </div>
+ <div class="tool-title">
+ {{ item.title }}
+ </div>
+ </div>
+ </div>
+ </div>
+ </el-card>
+ </div>
</template>
<script setup>
@@ -84,86 +73,89 @@
const router = useRouter();
// 鑾峰彇鍒楄〃
const toolList = ref([
- {
- id: 1,
- title: "鍦ㄧ嚎鍩硅",
- iconPath: new URL("@/assets/icons/icon1.png", import.meta.url).href,
- path: "/train",
- },
- {
- id: 2,
- title: "鎴戠殑鑰冭瘯",
- iconPath: new URL("@/assets/icons/icon2.png", import.meta.url).href,
- path: "/exam-list",
- },
- {
- id: 3,
- title: "鎴戠殑鎴愮哗",
- iconPath: new URL("@/assets/icons/icon2.png", import.meta.url).href,
- path: "/grade-list",
- },
+ {
+ id: 1,
+ title: "鍦ㄧ嚎鍩硅",
+ iconPath: new URL("@/assets/icons/icon1.png", import.meta.url).href,
+ path: "/train",
+ },
+ {
+ id: 2,
+ title: "鎴戠殑鑰冭瘯",
+ iconPath: new URL("@/assets/icons/icon2.png", import.meta.url).href,
+ path: "/exam-list",
+ },
+ {
+ id: 3,
+ title: "鎴戠殑鎴愮哗",
+ iconPath: new URL("@/assets/icons/icon2.png", import.meta.url).href,
+ path: "/grade-list",
+ },
]);
// 鑾峰彇棰滆壊
const getColor = computed(() => {
- return randomColor();
+ return randomColor();
});
// 鑾峰彇鐢ㄦ埛淇℃伅
const getFirstName = computed(() => {
- return userInfo.value.realName && userInfo.value.realName[0];
+ return userInfo.value.realName && userInfo.value.realName[0];
});
// 鐐瑰嚮浜嬩欢
const toolClick = (item) => {
- if (item.path) {
- router.push(item.path);
- }
+ if (item.path) {
+ router.push(item.path);
+ }
};
// 鐢ㄦ埛閫夐」
const dropdownRef = ref();
// 閫�鍑虹櫥褰�
const quit = () => {
- logout()
- .then(() => {
- router.push("/login").then(() => {
- userStore.setUserInfo(null);
- localStorage.clear("user");
- });
- })
- .catch((err) => {
- console.log("閫�鍑虹櫥褰曞け璐�,澶辫触鍘熷洜;", err);
- });
+ logout()
+ .then(() => {
+ router.push("/login").then(() => {
+ userStore.setUserInfo(null);
+ localStorage.clear("user");
+ });
+ })
+ .catch((err) => {
+ console.log("閫�鍑虹櫥褰曞け璐�,澶辫触鍘熷洜;", err);
+ });
+};
+const goPersonalCenter = () => {
+ router.push("/personal-center");
};
</script>
<style lang="scss" scoped>
.card {
- border-radius: 30px;
+ border-radius: 30px;
}
.avatar-content {
- width: 100%;
- height: 100%;
- display: flex;
- justify-content: center;
- align-items: center;
+ width: 100%;
+ height: 100%;
+ display: flex;
+ justify-content: center;
+ align-items: center;
}
.avatar-img {
- width: 100%;
- height: 100%;
- object-fit: cover;
+ width: 100%;
+ height: 100%;
+ object-fit: cover;
}
.avatar-container {
- cursor: pointer;
- color: var(--el-color-primary);
- display: flex;
- align-items: center;
+ cursor: pointer;
+ color: var(--el-color-primary);
+ display: flex;
+ align-items: center;
}
.example-showcase .el-dropdown-link {
- cursor: pointer;
- color: var(--el-color-primary);
- display: flex;
- align-items: center;
+ cursor: pointer;
+ color: var(--el-color-primary);
+ display: flex;
+ align-items: center;
}
</style>
diff --git a/src/views/personal-center/index.vue b/src/views/personal-center/index.vue
new file mode 100644
index 0000000..26980b4
--- /dev/null
+++ b/src/views/personal-center/index.vue
@@ -0,0 +1,195 @@
+<template>
+ <div
+ class="exam-list-container w-screen h-screen bg-slate-50 flex flex-col items-center"
+ >
+ <NormalHeader class="shrink-0"></NormalHeader>
+
+ <div class="list-container container grow relative">
+ <div
+ class="personal-center-box list-content absolute top-0 bottom-0 left-0 right-0 py-4"
+ >
+ <div class="information">
+ <el-card class="h-full" :body-style="{ height: '50%' }">
+ <div
+ class="card-wrapper w-full h-full flex flex-col px-8 box-border"
+ >
+ <div>涓汉淇℃伅</div>
+ <div class="img-box">
+ <input
+ type="file"
+ @change="changeHeadPortrait"
+ accept=".jpg, .png"
+ style="display: none"
+ ref="fileHeadPortrait"
+ id="fileHeadPortrait"
+ />
+ <img
+ class="img"
+ id="headPortrait"
+ @click="uploadImage"
+ :src="'api/files/' + userData.imagePath"
+ />
+ <span>{{ userData.userName }}</span>
+ </div>
+ <div>
+ <el-form label-width="auto" style="max-width: 600px">
+ <el-form-item label="濮撳悕">
+ {{ userData.realName }}
+ </el-form-item>
+ <el-form-item label="鐝骇">
+ {{ userData.className.join(",") }}
+ </el-form-item>
+ <el-form-item label="娉ㄥ唽鏃堕棿">
+ {{ timestampToDate(userData.createTime) }}
+ </el-form-item>
+ </el-form>
+ </div>
+ </div>
+ </el-card>
+ </div>
+ <div class="list-wrapper w-full h-full">
+ <el-card class="h-full" :body-style="{ height: '100%' }">
+ <el-tabs v-model="activeName" class="demo-tabs">
+ <el-tab-pane label="璧勬枡淇敼" name="information">
+ <el-form
+ :model="informationForm"
+ label-width="auto"
+ style="max-width: 600px"
+ >
+ <el-form-item label="鐪熷疄濮撳悕">
+ <el-input v-model="informationForm.name" />
+ </el-form-item>
+ <el-form-item label="骞撮緞">
+ <el-input v-model="informationForm.age" />
+ </el-form-item>
+ <el-form-item label="鎬у埆">
+ <el-select
+ v-model="informationForm.sex"
+ style="width: 100px"
+ >
+ <el-option label="鐢�" value="1" />
+ <el-option label="濂�" value="2" />
+ </el-select>
+ </el-form-item>
+ <el-form-item label="鍑虹敓骞存湀">
+ <el-date-picker
+ v-model="informationForm.birthDay"
+ type="date"
+ placeholder="Pick a day"
+ :size="size"
+ />
+ </el-form-item>
+ <el-form-item label="鎵嬫満">
+ <el-input
+ v-model="informationForm.phone"
+ /> </el-form-item></el-form
+ ></el-tab-pane>
+ <el-tab-pane label="瀵嗙爜淇敼" name="password">
+ <el-form
+ :model="passwordForm"
+ label-width="auto"
+ style="max-width: 600px"
+ >
+ <el-form-item label="鏃у瘑鐮�">
+ <el-input v-model="passwordForm.name" />
+ </el-form-item>
+ <el-form-item label="鏂板瘑鐮�">
+ <el-input v-model="passwordForm.name" />
+ </el-form-item>
+ <el-form-item label="纭瀵嗙爜">
+ <el-input v-model="passwordForm.name" />
+ </el-form-item>
+ </el-form>
+ </el-tab-pane>
+ </el-tabs>
+ </el-card>
+ </div>
+ </div>
+ </div>
+ </div>
+</template>
+
+<script setup>
+import { ref } from "vue";
+import { uploadImg } from "@/api/modules/personalCenter.js";
+import { ElMessage } from "element-plus";
+
+const activeName = ref("information");
+const userData = ref(JSON.parse(localStorage.getItem("user")).userInfo);
+const informationForm = ref({
+ name: userData.value.realName,
+ sex: userData.value.sex,
+ age: userData.value.age,
+ phone: userData.value.phone,
+ birthDay: userData.value.birthDay,
+});
+const passwordForm = ref({ name: "" });
+//澶村儚涓婁紶
+let formData = new FormData();
+const uploadImage = () => {
+ let logoFile = document.getElementById("fileHeadPortrait");
+ if (logoFile) {
+ logoFile.click();
+ }
+};
+const changeHeadPortrait = (e) => {
+ // let platformLogo = document.getElementById("headPortrait");
+ if (e.target.files[0]) {
+ // let reader = new FileReader();
+ // reader.onload = function (e) {
+ // if (platformLogo) {
+ // platformLogo.setAttribute("src", e.target.result);
+ // }
+ // };
+ // reader.readAsDataURL(e.target.files[0]);
+ formData.set("file", e.target.files[0]);
+ uploadImg(formData).then(
+ () => {
+ ElMessage({
+ showClose: true,
+ message: "涓婁紶鎴愬姛",
+ type: "success",
+ });
+ // window.location.reload();
+ },
+ (err) => {
+ ElMessage.error(err.data.errorMsg);
+ }
+ );
+ }
+};
+function timestampToDate(timestamp) {
+ const date = new Date(timestamp); // 灏嗘椂闂存埑杞崲涓篋ate瀵硅薄
+ const options = { year: "numeric", month: "long", day: "numeric" }; // 瀹氫箟鏃ユ湡鏍煎紡
+ return new Intl.DateTimeFormat("zh-CN", options).format(date); // 浣跨敤Intl.DateTimeFormat杩涜鏍煎紡鍖�
+}
+</script>
+
+<style lang="scss" scoped>
+:deep(.el-tabs__nav-wrap:after) {
+ display: none;
+}
+.personal-center-box {
+ display: flex;
+ justify-content: space-between;
+}
+.information {
+ width: 500px;
+ margin-right: 20px;
+}
+.img-box {
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ flex-direction: column;
+ margin-top: 30px;
+ margin-bottom: 30px;
+}
+.img {
+ height: 150px;
+ width: 150px;
+ border-radius: 100px;
+ overflow: hidden;
+ object-fit: cover;
+}
+</style>
diff --git a/vite.config.js b/vite.config.js
index 91c5690..6bccd72 100644
--- a/vite.config.js
+++ b/vite.config.js
@@ -30,7 +30,7 @@
proxy: {
'/api': {
// target: 'http://192.168.3.88:8000',
- target: 'http://42.193.1.25:8000',
+ target: 'http://192.168.3.64:8000',
changeOrigin: true,
}
}
--
Gitblit v1.8.0