Compare commits

...

6 Commits

Author SHA1 Message Date
zhaowenkang 5bf5a76272 bug修改 5 months ago
zhaowenkang 536506069e bug修改 5 months ago
zhaowenkang 9de048d82e bug修改 5 months ago
zhaowenkang 9e6782bf14 导出数据匹配修改 5 months ago
zhaowenkang 6d9bf01ffb 局域网内访问 5 months ago
zhaowenkang 4ac5d919ed 修改俱乐部的绑定 5 months ago
  1. 2
      work/package.json
  2. 4
      work/src/api/LoginApi.js
  3. 19
      work/src/api/index.js
  4. 26
      work/src/router/index.js
  5. 89
      work/src/views/AddWork.vue
  6. 366
      work/src/views/DoHomeworkView.vue
  7. 35
      work/src/views/HomeWork.vue
  8. 16
      work/src/views/Login.vue
  9. 403
      work/src/views/UpdateWork.vue
  10. 17
      work/src/views/WorkDetail.vue
  11. 563
      work/src/views/WorksShowView.vue
  12. 2
      work/vite.config.js

2
work/package.json

@ -4,7 +4,7 @@
"private": true, "private": true,
"type": "module", "type": "module",
"scripts": { "scripts": {
"dev": "vite",
"dev": "vite --host 0.0.0.0",
"build": "vite build", "build": "vite build",
"preview": "vite preview" "preview": "vite preview"
}, },

4
work/src/api/LoginApi.js

@ -5,8 +5,8 @@ const LoginApi={
return service.post("/api/login",username,password) return service.post("/api/login",username,password)
}, },
//退出登录 //退出登录
logout(token){
return service.post("/api/logout",token)
logout(){
return service.post("/api/logout")
} }
} }
export default LoginApi; export default LoginApi;

19
work/src/api/index.js

@ -18,6 +18,7 @@
import axios from "axios"; import axios from "axios";
import { useTokenStore } from "../stores/token"; import { useTokenStore } from "../stores/token";
const service = axios.create({ const service = axios.create({
// baseURL: 'http://192.168.8.191:8080', // baseURL: 'http://192.168.8.191:8080',
// baseURL: 'http://localhost:8080', // baseURL: 'http://localhost:8080',
@ -27,9 +28,9 @@ const service = axios.create({
// Axios的请求拦截器,在这里添加token到请求头 // Axios的请求拦截器,在这里添加token到请求头
axios.interceptors.request.use(config => { axios.interceptors.request.use(config => {
const token = useTokenStore();
if (token) {
config.headers.token = `${token}`;
const tokenStore = useTokenStore();
if (tokenStore.token) {
config.headers.token = tokenStore.token;
} }
return config; return config;
}, error => { }, error => {
@ -37,10 +38,10 @@ axios.interceptors.request.use(config => {
}); });
service.interceptors.request.use(config => { service.interceptors.request.use(config => {
const token = useTokenStore();
if (token) {
const tokenStore = useTokenStore();
if (tokenStore.token) {
// 一般后端会约定一个请求头的字段名来接收token,常见的如 'Authorization',并要求按照一定格式传递,比如 'Bearer <token>',这里按照此格式添加,你需要根据后端实际要求调整 // 一般后端会约定一个请求头的字段名来接收token,常见的如 'Authorization',并要求按照一定格式传递,比如 'Bearer <token>',这里按照此格式添加,你需要根据后端实际要求调整
config.headers.token = `${token}`;
config.headers.token =tokenStore.token;
} }
return config; return config;
}, error => { }, error => {
@ -58,14 +59,14 @@ service.interceptors.request.use(config => {
service.interceptors.response.use(response => { service.interceptors.response.use(response => {
return response.data; return response.data;
}, error =>{ }, error =>{
if(error.code == "500"){
if(error.code === "500"){
ElMessage.error("服务器错误!"); ElMessage.error("服务器错误!");
} }
const response = error.response; const response = error.response;
if(error.response && error.response.status == 403){
if(error.response && error.response.status === 403){
//提示一下权限不足 //提示一下权限不足
ElMessage.warning(response.data.message); ElMessage.warning(response.data.message);
} else if(response && response.status == 401){
} else if(response && response.code === 401){
//提示一下未登录 //提示一下未登录
ElMessage.warning(response.data.message); ElMessage.warning(response.data.message);
//跳转登录页面 //跳转登录页面

26
work/src/router/index.js

@ -1,11 +1,10 @@
import { createRouter, createWebHistory } from 'vue-router'; import { createRouter, createWebHistory } from 'vue-router';
import HomeWork from '../views/HomeWork.vue'; import HomeWork from '../views/HomeWork.vue';
import Login from '../views/Login.vue'; import Login from '../views/Login.vue';
import WorksShowView from '../views/WorksShowView.vue';
import DoHomeworkView from "@/views/DoHomeworkView.vue";
import AddWork from '../views/AddWork.vue'; import AddWork from '../views/AddWork.vue';
import WorkDetail from '../views/WorkDetail.vue'; import WorkDetail from '../views/WorkDetail.vue';
import UpdateWork from '../views/UpdateWork.vue'; import UpdateWork from '../views/UpdateWork.vue';
import { useTokenStore } from '../stores/token';
const router = createRouter({ const router = createRouter({
history: createWebHistory(), history: createWebHistory(),
@ -26,16 +25,6 @@ const router = createRouter({
component: AddWork component: AddWork
}, },
{ {
path: '/show',
name: 'workshow',
component: WorksShowView
},
{
path:'/doWork/:id?/:sub?',
name:'doWork',
component: DoHomeworkView
},
{
path:'/workdetail/:id', path:'/workdetail/:id',
name:'workdetail', name:'workdetail',
component: WorkDetail component: WorkDetail
@ -48,4 +37,17 @@ const router = createRouter({
] ]
}) })
// 添加全局前置守卫
router.beforeEach((to, from, next) => {
const tokenStore = useTokenStore();
const token = tokenStore.token;
if (!token && to.name !== 'login') {
// 如果没有token且要访问的不是登录页面,就跳转到登录页面
next({ name: 'login' });
} else {
// 有token或者要访问的是登录页面,正常放行
next();
}
});
export default router export default router

89
work/src/views/AddWork.vue

@ -29,11 +29,11 @@
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item label="关联文章"> <el-form-item label="关联文章">
<el-autocomplete v-model="articleTitle" :fetch-suggestions="queryArticleList" placeholder="请输入"
@select="handleSelectArticle" clearable @change="handleArticleChange"/>
<el-autocomplete v-model="articleTitle" :fetch-suggestions="queryArticleList" placeholder="请输入文章关键词"
@select="handleSelectArticle" clearable @clear="handleArticleClear"/>
</el-form-item> </el-form-item>
<el-form-item label="关联直播"> <el-form-item label="关联直播">
<el-select v-model="form.LiveId" placeholder="请选择" style="width: 100%" clearable @change="handleLiveChange">
<el-select v-model="form.LiveId" placeholder="请选择(可选择昨日、今日以及未来7日已创建的直播)" style="width: 100%" clearable @change="handleLiveChange">
<el-option v-for="item in live" :key="item.id" :label="item.name" :value="item.id" /> <el-option v-for="item in live" :key="item.id" :label="item.name" :value="item.id" />
</el-select> </el-select>
</el-form-item> </el-form-item>
@ -41,7 +41,7 @@
<div> <div>
<el-button type="primary" @click="addSingleChoice">添加单选</el-button> <el-button type="primary" @click="addSingleChoice">添加单选</el-button>
<el-button type="primary" @click="addMultipleChoice">添加多选</el-button> <el-button type="primary" @click="addMultipleChoice">添加多选</el-button>
<el-button type="primary" @click="addBlank">添加单选填空</el-button>
<el-button type="primary" @click="addBlank">添加简答题</el-button>
</div> </div>
</el-form-item> </el-form-item>
<div class="question-container" v-for="(question, index) in questions" :key="index" <div class="question-container" v-for="(question, index) in questions" :key="index"
@ -53,7 +53,8 @@
<div style="width: 600px;"> <div style="width: 600px;">
<el-input v-model="question.description" /> <el-input v-model="question.description" />
</div> </div>
<div class="add" v-if="question.type !== 'blank'">
<div class="add">
<div v-if="question.type !== 3">
<div class="question-option"> <div class="question-option">
<span>设置选项:</span> <span>设置选项:</span>
<el-button type="primary" text @click="addOption(index)">添加</el-button> <el-button type="primary" text @click="addOption(index)">添加</el-button>
@ -70,6 +71,7 @@
</div> </div>
</div> </div>
</div> </div>
</div>
<div class="delete" style="margin-left: 50px;"> <div class="delete" style="margin-left: 50px;">
<el-button type="info" plain @click="removeQuestion(index)">删除</el-button> <el-button type="info" plain @click="removeQuestion(index)">删除</el-button>
</div> </div>
@ -87,7 +89,7 @@
</template> </template>
<script lang="ts" setup> <script lang="ts" setup>
import { ref, onMounted, computed } from 'vue'
import { ref, onMounted, computed,reactive } from 'vue'
import AddWorkApi from '../api/AddWorkApi'; import AddWorkApi from '../api/AddWorkApi';
import _ from 'lodash'; import _ from 'lodash';
import dayjs from 'dayjs'; import dayjs from 'dayjs';
@ -100,6 +102,7 @@ import { useUserStore } from '../stores/user';
const router = useRouter(); const router = useRouter();
const options = ref([ const options = ref([
{ id: 1, name: '牧民俱乐部' }, { id: 1, name: '牧民俱乐部' },
{ id: 2, name: '博古论坛' }, { id: 2, name: '博古论坛' },
@ -127,7 +130,18 @@ const form = ref({
const articleTitle = ref(''); const articleTitle = ref('');
// //
const questions = ref([]); const questions = ref([]);
const onSubmit = () => { const onSubmit = () => {
let hasEmptyDescription = false;
questions.value.forEach(question => {
if (question.description === '') {
hasEmptyDescription = true;
}
});
if (hasEmptyDescription) {
ElMessage.error('存在题目未填写描述内容,请填写完整后再提交!');
return;
}
// picker // picker
if (form.value.picker && form.value.picker.length === 2) { if (form.value.picker && form.value.picker.length === 2) {
const startDate = dayjs(form.value.picker[0]).format('YYYY-MM-DD HH:mm:00'); const startDate = dayjs(form.value.picker[0]).format('YYYY-MM-DD HH:mm:00');
@ -137,13 +151,34 @@ const onSubmit = () => {
} }
form.value.Questions = questions.value; form.value.Questions = questions.value;
AddWorkApi.addWork(form.value) AddWorkApi.addWork(form.value)
.then(res => {
const code = res['code'];
const message=res['message']
if (code !== 200) {
ElMessage.error(message);
}else{
console.log(questions.value+'--------------') console.log(questions.value+'--------------')
ElMessage.success('添加成功');
router.push('/list')
}
});
} }
const back = () => { const back = () => {
window.history.back() window.history.back()
} }
const handleArticleClear=()=>{
articleTitle.value='';
form.value.ArticleId = '';
}
// const handleInputLimit = () => {
// if (form.value.Name.length > 22) {
// form.value.Name = form.value.Name.slice(0, 22);
// ElMessage.warning('22');
// }
// };
// //
const articleSearchResults = ref([]); const articleSearchResults = ref([]);
@ -152,7 +187,7 @@ const queryArticleList = async (queryString: string) => {
if (form.value.LiveId) { if (form.value.LiveId) {
ElMessage.warning('您已关联直播,暂无法关联文章'); ElMessage.warning('您已关联直播,暂无法关联文章');
articleTitle.value = ''; // articleTitle.value = ''; //
form.value.LiveId = '';
//form.value.LiveId = '';
return []; return [];
} }
try { try {
@ -165,6 +200,8 @@ const queryArticleList = async (queryString: string) => {
return formattedResults; return formattedResults;
} catch (error) { } catch (error) {
console.error('查询关联文章失败', error); console.error('查询关联文章失败', error);
ElMessage.error('请输入正确的文章关联词');
articleTitle.value = '';
return []; return [];
} }
}; };
@ -182,8 +219,8 @@ const handleLiveChange = () => {
if (form.value.ArticleId) { if (form.value.ArticleId) {
ElMessage.warning('您已关联文章,暂无法关联直播'); ElMessage.warning('您已关联文章,暂无法关联直播');
form.value.LiveId = ''; // form.value.LiveId = ''; //
form.value.ArticleId = '';
articleTitle.value = '';
//form.value.ArticleId = '';
//articleTitle.value = '';
} }
}; };
@ -231,27 +268,22 @@ const addMultipleChoice = () => {
}); });
}; };
//const hasAddedBlank=ref(false);
const addBlank = () => { const addBlank = () => {
// hasAddedBlanktrue
//if (!hasAddedBlank.value) {
questions.value.push({ questions.value.push({
type: 3, // 3 type: 3, // 3
description: '', description: '',
content: [{ "id": "", "text": "" }] content: [{ "id": "", "text": "" }]
}); });
// hasAddedBlank.value = true;
// }else {
// ElMessage.warning('');
// }
}; };
// const addOption = (questionIndex) => {
// const currentQuestion = questions.value[questionIndex];
// const currentContent = JSON.parse(currentQuestion.content);
// currentContent.push({ "id": "", "text": "" });
// currentQuestion.content = JSON.stringify(currentContent);
// };
// const removeOption = (questionIndex, optionIndex) => {
// const currentQuestion = questions.value[questionIndex];
// const currentContent = JSON.parse(currentQuestion.content);
// currentContent.splice(optionIndex, 1);
// currentQuestion.content = JSON.stringify(currentContent);
// };
const addOption = (questionIndex) => { const addOption = (questionIndex) => {
const currentQuestion = questions.value[questionIndex]; const currentQuestion = questions.value[questionIndex];
// content // content
@ -262,6 +294,21 @@ const addOption = (questionIndex) => {
}; };
const removeOption = (questionIndex, optionIndex) => { const removeOption = (questionIndex, optionIndex) => {
const currentQuestion = questions.value[questionIndex]; const currentQuestion = questions.value[questionIndex];
//
if (currentQuestion.type === 1) {
// 2
if (currentQuestion.content.length <= 1) {
ElMessage.warning('单选题至少需要保留一个选项,不能继续删除');
return;
}
}
if (currentQuestion.type === 2) {
// 2
if (currentQuestion.content.length <= 2) {
ElMessage.warning('多选题至少需要保留两个选项,不能继续删除');
return;
}
}
currentQuestion.content.splice(optionIndex, 1); currentQuestion.content.splice(optionIndex, 1);
}; };
const removeQuestion = (questionIndex) => { const removeQuestion = (questionIndex) => {

366
work/src/views/DoHomeworkView.vue

@ -1,366 +0,0 @@
<template>
<div class="container">
<div class="main">
<div class="content">
<div class="title">
{{ questionList[0].name }}
</div>
<template v-for="(question, questionIndex) in questionList" :key="questionIndex">
<!-- 单选 -->
<template v-if="question.type == 1">
<div class="question">
{{ questionIndex + 1 }}. {{ question.description }}单选
</div>
<div v-for="(answer, index) in question.content" :key="index" class="answer">
<div class="selected">
<input :id="`select-${questionIndex}-${index}`" :name="`radio-group-${questionIndex}`" type="radio"
v-model="selectedAnswers[questionIndex]"
:value="answer.text"
>
<label :for="`select-${questionIndex}-${index}`">{{ answer.text }}</label>
</div>
</div>
</template>
<!-- 多选 -->
<template v-if="question.type == 2">
<div class="question">
{{ questionIndex + 1 }}. {{ question.description }}多选
</div>
<div v-for="(answer, index) in question.content" :key="index" class="answer">
<div class="selected">
<input :id="`checkbox-${questionIndex}-${index}`" name="checkbox" type="checkbox"
v-model="selectedAnswers[questionIndex]"
:value="answer.text"
>
<label :for="`checkbox-${questionIndex}-${index}`">{{ answer.text }}</label>
</div>
</div>
</template>
<!-- 简答题 -->
<template v-if="question.type == 3">
<div class="Short-answers">
<div class="question">
{{ questionIndex + 1 }}. {{ question.description }}
</div>
<el-input
v-model="editorTitles[questionIndex]"
style="width: 100%; padding: 3.5%"
size="large"
placeholder="请输入标题(5-100字符)"
maxlength="100"
minlength="5"
show-word-limit
/>
<div class="editor">
<div style="border: 1px solid #ccc">
<Toolbar
style="border-bottom: 1px solid #ccc"
:editor="editorRefs[questionIndex]"
:defaultConfig="toolbarConfig"
:mode="mode"
/>
<Editor
style="height: 500px; overflow-y: hidden;"
v-model="editorContents[questionIndex]"
:defaultConfig="editorConfig"
:mode="mode"
@onCreated="editor => handleCreated(editor, questionIndex)"
/>
</div>
</div>
</div>
</template>
</template>
<!-- 提交按钮 -->
<div class="submit">
<img src="https://d31zlh4on95l9h.cloudfront.net/images/5iujb101000d2foxm6thylaa50qz6lgl.png" @click="submit">
</div>
<!-- 提交次数 -->
<div class="submit-times">
<span>您已提交{{sub}}每个作业可以提交3次</span>
</div>
</div>
</div>
</div>
</template>
<script setup>
import { onMounted, ref, shallowRef } from 'vue';
import homeworkApi from "@/api/HomeworkApi.js";
import { ElMessage } from "element-plus";
import '@wangeditor/editor/dist/css/style.css' // css
import { onBeforeUnmount } from 'vue'
import { Editor, Toolbar } from '@wangeditor/editor-for-vue'
import {useRoute, useRouter} from "vue-router";
const router = useRouter();
const route = useRoute();
let groupId = route.params.id;
let sub = route.params.sub;
// shallowRef
const editorRefs = ref([]);
// HTML
const editorContents = ref([]);
const editorTitles = ref([]);
// ajax
onMounted(() => {
setTimeout(() => {
editorContents.value = editorContents.value.map(() => '');
}, 1500)
})
const toolbarConfig = {
excludeKeys: [
'justify',
'table',
'codeBlock',
'divider',
'undo',
'redo',
'insertImage', //
'insertLink', //
'insertTable', //
'video',
'group-more-style',
'group-image',
'group-video',
'fullScreen',
'todo'
],
insertKeys: {
index: 0,
keys: ['bold', 'italic']
}
}
const editorConfig = {
placeholder: '请输入内容...',
toolbarKeys: toolbarConfig.toolbarKeys
}
//
onBeforeUnmount(() => {
editorRefs.value.forEach(editor => {
if (editor == null) return;
editor.destroy();
});
})
const handleCreated = (editor, questionIndex) => {
editorRefs.value[questionIndex] = editor; // editor
editor.config.toolbarConfig = toolbarConfig; //
}
const questionList = ref([]);
function getQuestionList() {
console.log("ljghasjkhdjksahjkhsajkhjkasd",groupId);
homeworkApi.getHomeworkQuestion(groupId).then(resp => {
if (resp.code == 200) {
questionList.value = resp.data;
for (let i = 0; i < questionList.value.length; i++) {
questionList.value[i].content = JSON.parse(questionList.value[i].content);
// editorTitles editorContents
editorTitles.value.push('');
editorContents.value.push('');
// selectedAnswers
selectedAnswers.value.push([]);
}
} else {
ElMessage.error("未知错误,请联系管理员");
}
});
}
getQuestionList();
//
const homework = ref([]);
const selectedAnswers = ref([]);
questionList.value.forEach(() => {
selectedAnswers.value.push([]);
});
// groupId
function submit() {
homework.value = [];
for (let i = 0; i < questionList.value.length; i++) {
if (questionList.value[i].type == 1 || questionList.value[i].type == 2) {
homework.value.push({
"id": questionList.value[i].id,
"answer": selectedAnswers.value[i],
"type": questionList.value[i].type
});
} else if (questionList.value[i].type == 3) {
const editor = editorRefs.value[i];
const plainText = editor ? editor.getText() : '';
homework.value.push({
"id": questionList.value[i].id,
"answer": [editorTitles.value[i], plainText],
"type": questionList.value[i].type
});
}
}
let groupId = route.params.id;
let sub = route.params.sub;
if (sub <=2){
homeworkApi.submitHomework(homework.value, groupId).then(resp => {
if (resp.code == 200) {
ElMessage.success("提交成功");
homework.value = [];
router.push("/show");
} else {
ElMessage.error("未知错误,请联系管理员");
}
});
}else {
ElMessage.error("提交失败您,已提交3次,每个作业可以提交3次");
}
}
</script>
<style scoped>
.container {
text-align: center;
margin-left: auto;
margin-right: auto;
width: 34.375rem;
height: 114.399375rem;
}
.main {
background-image: url("https://lfjf.rzfwq.com/jtzy/Product/pcjingwang/images/20230823/qiangdianbanHomeWorkBg.png");
background-size: contain;
background-position: center 0;
background-repeat: no-repeat;
margin: 0;
width: 100%;
height: 1830px;
text-align: center;
position: relative;
}
.content {
position: absolute;
width: 93%;
height: 80%;
overflow-y: scroll;
/* 居中显示 */
left: 50%;
transform: translate(-50%, 0);
top: 12.5%;
text-align: left;
}
/* 滚动条样式 */
.content::-webkit-scrollbar {
width: 3px;
}
.content::-webkit-scrollbar-track {
background: #f1f1f1; /* 滚动条轨道的背景色 */
}
.content::-webkit-scrollbar-thumb {
background: #d9d9d9; /* 滚动条滑块的颜色 */
border-radius: 6px; /* 滑块的圆角 */
}
.title {
font-size: 1.65rem;
font-weight: 600;
/* 居中显示 */
text-align: center;
/*字体颜色*/
color: #3f27b1;
}
.question {
padding-top: 10%;
padding-left: 4%;
font-size: 1.35rem;
font-weight: 500;
}
.answer {
padding-top: 2.5%;
padding-left: 7%;
font-size: 1.35rem;
}
.selected {
display: block;
padding: 1% 0 1.2% 0;
}
.selected input[name="checkbox"] {
margin-right: 1%;
width: 1.2rem;
height: 1rem;
/* 透明度 */
opacity: 0.8;
cursor: pointer; /* 鼠标悬停时变成手的形状 */
}
.selected input[type="radio"]{
margin-right: 1%;
width: 1.2rem;
height: 1rem;
/* 透明度 */
opacity: 0.8;
cursor: pointer; /* 鼠标悬停时变成手的形状 */
}
/* 单选按钮选中时的样式 */
.selected input[type="radio"]:checked {
accent-color: blue; /* 设置选中时的颜色为蓝色 */
}
/* 多选按钮选中时的样式 */
.selected input[type="checkbox"]:checked {
accent-color: blue; /* 设置选中时的颜色为蓝色 */
}
.selected label {
cursor: pointer;
}
.editor {
padding-top: 2.5%;
padding-left: 3.5%;
padding-right: 3.5%;
height: 30rem;
}
.Short-answers {
height: 48rem;
}
.submit {
display: block;
text-align: center;
}
.submit img {
padding-top: 2.5%;
padding-left: 3.5%;
padding-right: 3.5%;
cursor: pointer;
width: 67%;
}
.submit-times {
font-size: 0.8rem;
color: #858585;
text-align: center;
}
</style>

35
work/src/views/HomeWork.vue

@ -21,15 +21,15 @@
<el-table-column prop="name" label="作业名称"></el-table-column> <el-table-column prop="name" label="作业名称"></el-table-column>
<el-table-column label="内容归属"> <el-table-column label="内容归属">
<template v-slot="scope"> <template v-slot="scope">
<span v-if="scope.row.clubType === '1'">牧民俱乐部</span>
<span v-else-if="scope.row.clubType === '2'">博古论坛</span>
<span v-else-if="scope.row.clubType === '3'">神枪手俱乐部</span>
<span v-else-if="scope.row.clubType === '4'">环球俱乐部</span>
<span v-else-if="scope.row.clubType === '5'">价值投资</span>
<span v-else-if="scope.row.clubType === '6'">波段行情</span>
<span v-else-if="scope.row.clubType === '7'">抄底卖顶</span>
<span v-else-if="scope.row.clubType === '8'">资金及仓位管理</span>
<span v-else>财富的游戏</span>
<span v-if="scope.row.clubType == '1'">牧民俱乐部</span>
<span v-else-if="scope.row.clubType == '2'">博古论坛</span>
<span v-else-if="scope.row.clubType == '3'">神枪手俱乐部</span>
<span v-else-if="scope.row.clubType == '4'">环球俱乐部</span>
<span v-else-if="scope.row.clubType == '5'">价值投资</span>
<span v-else-if="scope.row.clubType == '6'">波段行情</span>
<span v-else-if="scope.row.clubType == '7'">抄底卖顶</span>
<span v-else-if="scope.row.clubType == '8'">资金及仓位管理</span>
<span v-else-if="scope.row.clubType == '9'">财富的游戏</span>
</template> </template>
</el-table-column> </el-table-column>
<el-table-column prop="article" label="关联文章"> <el-table-column prop="article" label="关联文章">
@ -58,7 +58,7 @@
</el-table-column> </el-table-column>
<el-table-column prop="status" label="状态"> <el-table-column prop="status" label="状态">
<template #default="{ row }"> <template #default="{ row }">
<span v-if="row.status === 0">上架</span>
<span v-if="row.status === 0">发布</span>
<span v-else-if="row.status === 1">发布中</span> <span v-else-if="row.status === 1">发布中</span>
<span v-else-if="row.status === 2">已下架</span> <span v-else-if="row.status === 2">已下架</span>
</template> </template>
@ -130,6 +130,11 @@ const getAssignments = (PageNo, PageSize) => {
//mounted //mounted
onMounted(() => { onMounted(() => {
getAssignments(PageNo.value, PageSize.value); getAssignments(PageNo.value, PageSize.value);
const token = useTokenStore();
console.log(token);
console.log(token.value);
console.log(token.token)
console.log("=============");
}); });
const newAssignment = () => { const newAssignment = () => {
@ -188,15 +193,17 @@ const editAssignment = async (row) => {
// } // }
//退 //退
function logout(){
const logout=async()=>{
try {
await LoginApi.logout()
} catch (error) {
console.log(error)
}
// //
const tokenStore = useTokenStore(); const tokenStore = useTokenStore();
const userStore = useUserStore(); const userStore = useUserStore();
tokenStore.clear(); tokenStore.clear();
userStore.clear(); userStore.clear();
LoginApi.logout().then(res => {
console.log(res)
})
router.push('/') router.push('/')
} }
</script> </script>

16
work/src/views/Login.vue

@ -28,6 +28,7 @@ import LoginApi from '../api/LoginApi';
import { ElMessage } from 'element-plus'; import { ElMessage } from 'element-plus';
import { useRouter } from 'vue-router'; import { useRouter } from 'vue-router';
import axios from 'axios'; import axios from 'axios';
import { useTokenStore } from '../stores/token';
// 使ref // 使ref
const username = ref(''); const username = ref('');
const password = ref(''); const password = ref('');
@ -50,18 +51,14 @@ const login = async () => {
if (response.code === 200) { if (response.code === 200) {
// token // token
token.value = response.data.token; token.value = response.data.token;
// tokenlocalStorage'token'
localStorage.setItem('token', token.value);
// axiostoken
axios.interceptors.request.use(config => {
//config.headers.token = `${token.value}`;
config.headers['token'] = token.value;
return config;
});
const tokenStore=useTokenStore();
tokenStore.changeToken(token.value);
// const userStore=useUserStore();
// userStore.changeUser(response.data.user);
console.log(token.value); console.log(token.value);
console.log("=--------");
// //
ElMessage.success('登录成功'); ElMessage.success('登录成功');
// //
router.push('/list'); router.push('/list');
} else { } else {
@ -72,7 +69,6 @@ const login = async () => {
// //
ElMessage.error('网络异常,请检查网络连接后重试'); ElMessage.error('网络异常,请检查网络连接后重试');
console.error(error); console.error(error);
} }
}; };
</script> </script>

403
work/src/views/UpdateWork.vue

@ -3,119 +3,192 @@
<el-container> <el-container>
<el-header class="header"> <el-header class="header">
<el-text class="header-text">抢点班作业后台管理</el-text> <el-text class="header-text">抢点班作业后台管理</el-text>
<el-button class="header-button" type="primary" text style="float: right;" @click="logout">退出登录</el-button>
<el-button
class="header-button"
type="primary"
text
style="float: right"
@click="logout"
>退出登录</el-button
>
</el-header> </el-header>
<el-main class="main"> <el-main class="main">
<div class="main-title"> <div class="main-title">
<div class="main-title-text" style="float: left;">
编辑作业
</div>
<div class="main-title-text" style="float: left">编辑作业</div>
<div> <div>
<el-button class="main-button" @click="back">返回上一页</el-button> <el-button class="main-button" @click="back">返回上一页</el-button>
</div> </div>
</div> </div>
<div class="main-back"> <div class="main-back">
<el-form :model="form" label-width="auto" style="max-width: 700px" size="large">
<el-form
:model="form"
label-width="auto"
style="max-width: 700px"
size="large"
>
<el-form-item label="作业名称"> <el-form-item label="作业名称">
<el-input v-model="form.Name" placeholder="请输入"></el-input> <el-input v-model="form.Name" placeholder="请输入"></el-input>
</el-form-item> </el-form-item>
<el-form-item label="提交时间" style="width: 70%"> <el-form-item label="提交时间" style="width: 70%">
<el-date-picker v-model="form.picker" type="daterange" range-separator="" start-placeholder="开始日期"
end-placeholder="结束日期" />
<el-date-picker
v-model="form.picker"
type="daterange"
range-separator="至"
start-placeholder="开始日期"
end-placeholder="结束日期"
/>
</el-form-item> </el-form-item>
<el-form-item label="作业归属"> <el-form-item label="作业归属">
<el-select v-model="form.ClubType" placeholder="请选择" style="width: 100%">
<el-option v-for="item in options" :key="item.id" :label="item.name" :value="item.id" />
<el-select
v-model="form.ClubType"
placeholder="请选择"
style="width: 100%"
>
<el-option
v-for="item in options"
:key="item.id"
:label="item.name"
:value="item.id"
/>
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item label="关联文章"> <el-form-item label="关联文章">
<el-autocomplete v-model="articleTitle" :fetch-suggestions="queryArticleList" placeholder="请输入"
@select="handleSelectArticle" clearable />
<el-autocomplete
v-model="articleTitle"
:fetch-suggestions="queryArticleList"
placeholder="请输入文章关键词"
@select="handleSelectArticle"
clearable
/>
</el-form-item> </el-form-item>
<el-form-item label="关联直播"> <el-form-item label="关联直播">
<el-select v-model="form.LiveId" placeholder="请选择" style="width: 100%" clearable
@change="handleLiveChange">
<el-option v-for="item in live" :key="item.id" :label="item.name" :value="item.id" />
<el-select
v-model="form.LiveId"
placeholder="请选择(可选择昨日、今日以及未来7日已创建的直播)"
style="width: 100%"
clearable
@change="handleLiveChange"
>
<el-option
v-for="item in live"
:key="item.id"
:label="item.name"
:value="item.id"
/>
</el-select> </el-select>
</el-form-item> </el-form-item>
<el-form-item label="选择类型"> <el-form-item label="选择类型">
<div> <div>
<el-button type="primary" @click="addSingleChoice">添加单选</el-button>
<el-button type="primary" @click="addMultipleChoice">添加多选</el-button>
<el-button type="primary" @click="addBlank">添加单选填空</el-button>
<el-button type="primary" @click="addSingleChoice"
>添加单选</el-button
>
<el-button type="primary" @click="addMultipleChoice"
>添加多选</el-button
>
<el-button type="primary" @click="addBlank"
>添加简答题</el-button
>
</div> </div>
</el-form-item> </el-form-item>
<div class="question-container" v-for="(question, index) in questions" :key="index"
:class="{ 'bg-change': isHovered[index] }" @mouseenter="handleMouseEnter(index)"
@mouseleave="handleMouseLeave(index)">
<div
class="question-container"
v-for="(question, index) in questions"
:key="index"
:class="{ 'bg-change': isHovered[index] }"
@mouseenter="handleMouseEnter(index)"
@mouseleave="handleMouseLeave(index)"
>
<div class="question-title"> <div class="question-title">
{{ questionPrefix(index) }} {{ getQuestionTypeText(question.type) }}
{{ questionPrefix(index) }}
{{ getQuestionTypeText(question.type) }}
</div> </div>
<div style="width: 600px;">
<div style="width: 600px">
<el-input v-model="question.description" /> <el-input v-model="question.description" />
</div> </div>
<div class="add" v-if="question.type !== 'blank'">
<div class="add">
<div v-if="question.type !== 3">
<div class="question-option"> <div class="question-option">
<span>设置选项:</span> <span>设置选项:</span>
<el-button type="primary" text @click="addOption(index)">添加</el-button>
<el-button type="primary" text @click="addOption(index)"
>添加</el-button
>
</div> </div>
<div v-for="(option, optionIndex) in question.content" :key="optionIndex">
<div class="select" style="display: flex;">
<div class="selection-item" style="display: flex;">
<div style="width: 550px;">
<el-input v-model="question.content[optionIndex].text" />
<div
v-for="(option, optionIndex) in question.content"
:key="optionIndex"
>
<div class="select" style="display: flex">
<div class="selection-item" style="display: flex">
<div style="width: 550px">
<el-input
v-model="question.content[optionIndex].text"
/>
</div> </div>
<div> <div>
<el-button type="primary" text @click="removeOption(index, optionIndex)">删除</el-button>
<el-button
type="primary"
text
@click="removeOption(index, optionIndex)"
>删除</el-button
>
</div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
<div class="delete" style="margin-left: 50px;">
<el-button type="info" plain @click="removeQuestion(index)">删除</el-button>
<div class="delete" style="margin-left: 50px">
<el-button type="info" plain @click="removeQuestion(index)"
>删除</el-button
>
</div> </div>
</div> </div>
</div> </div>
<div class="submit"> <div class="submit">
<el-button type="primary" :disabled="!form.Name || !form.picker" @click="onSubmit">确认</el-button>
<el-button
type="primary"
:disabled="!form.Name || !form.picker"
@click="onSubmit"
>确认</el-button
>
</div> </div>
</el-form> </el-form>
</div> </div>
</el-main> </el-main>
</el-container> </el-container>
</div> </div>
</template> </template>
<script lang="ts" setup> <script lang="ts" setup>
import { ref, onMounted, computed } from 'vue'
import { useRouter, useRoute } from 'vue-router';
import AddWorkApi from '../api/AddWorkApi';
import _ from 'lodash';
import dayjs from 'dayjs';
import ClassListApi from '../api/ClassListApi';
import { ElMessage } from 'element-plus';
import LoginApi from '../api/LoginApi';
import { useTokenStore } from '../stores/token';
import { useUserStore } from '../stores/user';
import { ref, onMounted, computed, reactive } from "vue";
import { useRouter, useRoute } from "vue-router";
import AddWorkApi from "../api/AddWorkApi";
import _ from "lodash";
import dayjs from "dayjs";
import ClassListApi from "../api/ClassListApi";
import { ElMessage } from "element-plus";
import LoginApi from "../api/LoginApi";
import { useTokenStore } from "../stores/token";
import { useUserStore } from "../stores/user";
import { ar } from "date-fns/locale";
import { el } from "element-plus/es/locale";
const router = useRouter(); const router = useRouter();
const options = ref([ const options = ref([
{ id: 1, name: '牧民俱乐部' },
{ id: 2, name: '博古论坛' },
{ id: 3, name: '神枪手俱乐部' },
{ id: 4, name: '环球俱乐部' },
{ id: 5, name: '价值投资' },
{ id: 6, name: '波段行情' },
{ id: 7, name: '抄底卖顶' },
{ id: 8, name: '资金及仓位管理' },
{ id: 9, name: '财富的游戏' },
{ id: 1, name: "牧民俱乐部" },
{ id: 2, name: "博古论坛" },
{ id: 3, name: "神枪手俱乐部" },
{ id: 4, name: "环球俱乐部" },
{ id: 5, name: "价值投资" },
{ id: 6, name: "波段行情" },
{ id: 7, name: "抄底卖顶" },
{ id: 8, name: "资金及仓位管理" },
{ id: 9, name: "财富的游戏" },
]); ]);
const route = useRoute(); const route = useRoute();
const id = ref(route.params.id)
console.log(id.value + '============')
const id = ref(route.params.id);
console.log(id.value + "============");
// //
const homeworkData = ref<{ const homeworkData = ref<{
@ -133,22 +206,21 @@ const homeworkData = ref<{
}; };
status: number; status: number;
form: FormItemType[]; form: FormItemType[];
}>({ }>({
name: '',
startDate: '',
endDate: '',
clubType: '',
name: "",
startDate: "",
endDate: "",
clubType: "",
article: { article: {
id: '',
title: '',
id: "",
title: "",
}, },
live: { live: {
id: '',
name: ''
id: "",
name: "",
}, },
status: 0, status: 0,
form: []
form: [],
}); });
// form // form
@ -165,17 +237,16 @@ interface FormItemType {
updatedAt: string; updatedAt: string;
} }
const form = ref({ const form = ref({
id: '',
Name: '',
ClubType: '',
ArticleId: '',
LiveId: '',
id: "",
Name: "",
ClubType: "",
ArticleId: "",
LiveId: "",
picker: [], picker: [],
StartDate: '',
EndDate: '',
Questions: []
StartDate: "",
EndDate: "",
Questions: [],
}); });
// false // false
@ -184,13 +255,13 @@ onMounted(async () => {
try { try {
const response = await ClassListApi.getClassListOne(id.value); const response = await ClassListApi.getClassListOne(id.value);
homeworkData.value = response.data; homeworkData.value = response.data;
console.log(homeworkData.value)
console.log(homeworkData.value);
form.value.Name = homeworkData.value.name; form.value.Name = homeworkData.value.name;
// //
isPublished.value = homeworkData.value.status; isPublished.value = homeworkData.value.status;
const start = dayjs(homeworkData.value.startDate).format('YYYY-MM-DD');
const end = dayjs(homeworkData.value.endDate).format('YYYY-MM-DD');
const start = dayjs(homeworkData.value.startDate).format("YYYY-MM-DD");
const end = dayjs(homeworkData.value.endDate).format("YYYY-MM-DD");
form.value.picker = [start, end]; form.value.picker = [start, end];
if (homeworkData.value.article && homeworkData.value.article.title) { if (homeworkData.value.article && homeworkData.value.article.title) {
@ -203,7 +274,10 @@ onMounted(async () => {
const newQuestions = []; const newQuestions = [];
homeworkData.value.form.forEach((formItem: FormItemType) => { homeworkData.value.form.forEach((formItem: FormItemType) => {
// contentJSON // contentJSON
const contentArray = JSON.parse(formItem.content) as { id: string, text: string }[];
const contentArray = JSON.parse(formItem.content) as {
id: string;
text: string;
}[];
// questions // questions
const question = { const question = {
id: formItem.id, id: formItem.id,
@ -223,89 +297,120 @@ onMounted(async () => {
}; };
questions.value = processFormData(); questions.value = processFormData();
} catch (error) { } catch (error) {
console.error('接口请求出现错误:', error);
console.error("接口请求出现错误:", error);
} }
}); });
const articleTitle = ref('');
const articleTitle = ref("");
// //
const questions = ref([]); const questions = ref([]);
const onSubmit = () => { const onSubmit = () => {
let hasEmptyDescription = false;
questions.value.forEach(question => {
if (question.description === '') {
hasEmptyDescription = true;
}
});
if (hasEmptyDescription) {
ElMessage.error('存在题目未填写描述内容,请填写完整后再提交!');
return;
}
// picker // picker
if (form.value.picker && form.value.picker.length === 2) { if (form.value.picker && form.value.picker.length === 2) {
const startDate = dayjs(form.value.picker[0]).format('YYYY-MM-DD HH:mm:00');
const endDate = dayjs(form.value.picker[1]).format('YYYY-MM-DD HH:mm:00');
const startDate = dayjs(form.value.picker[0]).format("YYYY-MM-DD HH:mm:00");
const endDate = dayjs(form.value.picker[1]).format("YYYY-MM-DD HH:mm:00");
form.value.StartDate = startDate; form.value.StartDate = startDate;
form.value.EndDate = endDate; form.value.EndDate = endDate;
} }
form.value.Questions = questions.value; form.value.Questions = questions.value;
if (
isLiveChange.value === false &&
homeworkData.value.live &&
homeworkData.value.live.id
) {
form.value.LiveId = homeworkData.value.live.id;
}
if (form.value.LiveId) { if (form.value.LiveId) {
// form.value.liveid使liveidArticleIdliveid // form.value.liveid使liveidArticleIdliveid
form.value.ArticleId = '';
form.value.ArticleId = "";
articleTitle.value = "";
} else if (form.value.ArticleId) { } else if (form.value.ArticleId) {
// 使idform.value.ArticleId // 使idform.value.ArticleId
} else if (homeworkData.value.article && homeworkData.value.article.id) { } else if (homeworkData.value.article && homeworkData.value.article.id) {
// 使idhomeworkData.value.article.id // 使idhomeworkData.value.article.id
form.value.ArticleId = homeworkData.value.article.id; form.value.ArticleId = homeworkData.value.article.id;
} }
if (typeof id.value === 'string') {
if (typeof id.value === "string") {
form.value.id = id.value; form.value.id = id.value;
} }
ClassListApi.editWork(form.value)
.then((response) => {
if (!form.value.ArticleId && !form.value.LiveId) {
ElMessage.error("编辑失败,请选择关联文章或关联直播");
} else {
ClassListApi.editWork(form.value).then((response) => {
const code = response["code"];
const message = response["message"];
if (code !== 200) {
ElMessage.error(message);
} else {
console.log(response); console.log(response);
ElMessage.success('编辑成功');
router.push('/list')
})
.catch((error) => {
console.error('编辑失败', error);
ElMessage.error('编辑失败');
ElMessage.success("编辑成功");
router.push("/list");
}
}); });
console.log(id.value + '--------------')
console.log(form.value)
} }
console.log(id.value + "--------------");
console.log(form.value);
};
const back = () => { const back = () => {
window.history.back()
}
window.history.back();
};
// //
const articleSearchResults = ref([]); const articleSearchResults = ref([]);
// //
const queryArticleList = async (queryString: string) => { const queryArticleList = async (queryString: string) => {
if (form.value.LiveId) { if (form.value.LiveId) {
ElMessage.warning('您已关联直播,暂无法关联文章');
articleTitle.value = ''; //
form.value.LiveId = '';
ElMessage.warning("您已关联直播,暂无法关联文章");
articleTitle.value = ""; //
//form.value.LiveId = ''; //()
return []; return [];
} }
try { try {
const response = await AddWorkApi.getArticleList(queryString); const response = await AddWorkApi.getArticleList(queryString);
const formattedResults = response.data.map(article => ({
const formattedResults = response.data.map((article) => ({
value: article.title, value: article.title,
label: article.id
label: article.id,
})); }));
articleSearchResults.value = formattedResults; articleSearchResults.value = formattedResults;
return formattedResults; return formattedResults;
} catch (error) { } catch (error) {
console.error('查询关联文章失败', error);
console.error("查询关联文章失败", error);
ElMessage.error("请输入正确的文章关联词");
articleTitle.value = "";
return []; return [];
} }
}; };
//
const isLiveChange = ref(false);
const handleLiveChange = () => { const handleLiveChange = () => {
if (form.value.ArticleId) {
ElMessage.warning('您已关联文章,暂无法关联直播');
form.value.LiveId = ''; //
form.value.ArticleId = '';
articleTitle.value = '';
isLiveChange.value = true;
if (articleTitle.value) {
ElMessage.warning("您已关联文章,暂无法关联直播");
form.value.LiveId = ""; //
form.value.ArticleId = "";
//articleTitle.value = ''; ()
} }
}; };
// //
const handleSelectArticle = (article: { label: string }) => { const handleSelectArticle = (article: { label: string }) => {
// idarticle.label使 // idarticle.label使
console.log('选中的文章id', article.label);
console.log("选中的文章id", article.label);
form.value.ArticleId = article.label; // id form.value.ArticleId = article.label; // id
const selectedArticle = articleSearchResults.value.find(a => a.label === article.label);
const selectedArticle = articleSearchResults.value.find(
(a) => a.label === article.label
);
if (selectedArticle) { if (selectedArticle) {
articleTitle.value = selectedArticle.value; // articleTitle.value = selectedArticle.value; //
} }
@ -315,13 +420,13 @@ const handleSelectArticle = (article: { label: string }) => {
const live = ref([]); const live = ref([]);
function getLive() { function getLive() {
AddWorkApi.getLiveList() AddWorkApi.getLiveList()
.then(res => {
.then((res) => {
live.value = res.data; live.value = res.data;
console.log(live.value); console.log(live.value);
}) })
.catch(error => {
console.error('获取直播列表失败', error)
})
.catch((error) => {
console.error("获取直播列表失败", error);
});
} }
getLive(); getLive();
@ -329,52 +434,59 @@ getLive();
const getQuestionTypeText = (type) => { const getQuestionTypeText = (type) => {
switch (type) { switch (type) {
case 1: case 1:
return '作业题目(单选)';
return "作业题目(单选)";
case 2: case 2:
return '作业题目(多选)';
return "作业题目(多选)";
case 3: case 3:
return '作业题目(简答题)';
return "作业题目(简答题)";
default: default:
return '未知类型题目';
return "未知类型题目";
} }
}; };
const addSingleChoice = () => { const addSingleChoice = () => {
if (isPublished.value === 1) { if (isPublished.value === 1) {
ElMessage.warning('处于发布中,不能添加新题目');
ElMessage.warning("处于发布中,不能添加新题目");
} else { } else {
questions.value.push({ questions.value.push({
type: 1, // 1 type: 1, // 1
description: '',
content: [{ "id": "", "text": "" }, { "id": "", "text": "" }]
description: "",
content: [
{ id: "", text: "" },
{ id: "", text: "" },
],
}); });
} }
}; };
const addMultipleChoice = () => { const addMultipleChoice = () => {
if (isPublished.value === 1) { if (isPublished.value === 1) {
ElMessage.warning('处于发布中,不能添加新题目');
ElMessage.warning("处于发布中,不能添加新题目");
} else { } else {
questions.value.push({ questions.value.push({
type: 2, // 2 type: 2, // 2
description: '',
content: [{ "id": "", "text": "" }, { "id": "", "text": "" }]
description: "",
content: [
{ id: "", text: "" },
{ id: "", text: "" },
],
}); });
} }
}; };
//const hasAddedBlank=ref(false);
const addBlank = () => { const addBlank = () => {
if (isPublished.value === 1) {
ElMessage.warning('处于发布中,不能添加新题目');
} else {
// hasAddedBlanktrue
//if (!hasAddedBlank.value) {
questions.value.push({ questions.value.push({
type: 3, // 3 type: 3, // 3
description: '', description: '',
content: [{ "id": "", "text": "" }] content: [{ "id": "", "text": "" }]
}); });
}
// hasAddedBlank.value = true;
// }else {
// ElMessage.warning('');
// }
}; };
const addOption = (questionIndex) => { const addOption = (questionIndex) => {
@ -387,12 +499,26 @@ const addOption = (questionIndex) => {
}; };
const removeOption = (questionIndex, optionIndex) => { const removeOption = (questionIndex, optionIndex) => {
const currentQuestion = questions.value[questionIndex]; const currentQuestion = questions.value[questionIndex];
//
if (currentQuestion.type === 1) {
if (currentQuestion.content.length <= 1) {
ElMessage.warning("单选题至少需要保留一个选项,不能继续删除");
return;
}
}
if (currentQuestion.type === 2) {
// 2
if (currentQuestion.content.length <= 2) {
ElMessage.warning("多选题至少需要保留两个选项,不能继续删除");
return;
}
}
currentQuestion.content.splice(optionIndex, 1); currentQuestion.content.splice(optionIndex, 1);
}; };
const removeQuestion = (questionIndex) => { const removeQuestion = (questionIndex) => {
if (isPublished.value === 1) { if (isPublished.value === 1) {
ElMessage.warning('处于发布中,不能删除题目');
ElMessage.warning("处于发布中,不能删除题目");
} else { } else {
questions.value.splice(questionIndex, 1); questions.value.splice(questionIndex, 1);
} }
@ -403,7 +529,7 @@ const questionPrefix = computed(() => {
return (index) => { return (index) => {
return `${index + 1}`; return `${index + 1}`;
}; };
})
});
// false // false
const isHovered = ref(Array(questions.value.length).fill(false)); const isHovered = ref(Array(questions.value.length).fill(false));
@ -420,7 +546,6 @@ onMounted(() => {
isHovered.value = Array(questions.value.length).fill(false); isHovered.value = Array(questions.value.length).fill(false);
}); });
//退 //退
function logout() { function logout() {
// //
@ -428,10 +553,10 @@ function logout() {
const userStore = useUserStore(); const userStore = useUserStore();
tokenStore.clear(); tokenStore.clear();
userStore.clear(); userStore.clear();
LoginApi.logout().then(res => {
console.log(res)
})
router.push('/')
LoginApi.logout().then((res) => {
console.log(res);
});
router.push("/");
} }
</script> </script>
@ -496,7 +621,7 @@ function logout() {
.main { .main {
padding: 30px 212px; padding: 30px 212px;
background-color: #F8F8F8;
background-color: #f8f8f8;
} }
.main-title { .main-title {

17
work/src/views/WorkDetail.vue

@ -18,7 +18,7 @@
<div class="table-container"> <div class="table-container">
<div class="search-bar" :v-model="form"> <div class="search-bar" :v-model="form">
<el-input v-model="form.jwcode" type="text" placeholder="请输入精网号" style="width: 180px;" <el-input v-model="form.jwcode" type="text" placeholder="请输入精网号" style="width: 180px;"
size="large" />
size="large" clearable />
<el-select v-model="form.deptId" placeholder="选择分店门部" size="large" <el-select v-model="form.deptId" placeholder="选择分店门部" size="large"
style="width: 180px; margin-left: 15px;" clearable @change="handleDeptSelect"> style="width: 180px; margin-left: 15px;" clearable @change="handleDeptSelect">
<el-option v-for="item in dept" :key="item.id" :label="item.deptName" <el-option v-for="item in dept" :key="item.id" :label="item.deptName"
@ -51,13 +51,13 @@
</el-table-column> </el-table-column>
<el-table-column label="作业详情"> <el-table-column label="作业详情">
<template v-slot="{ $index }"> <template v-slot="{ $index }">
<el-popover placement="bottom" title="详情" :width="500" trigger="click">
<el-popover placement="bottom" title="作业详情" :width="500" trigger="click">
<template #reference> <template #reference>
<el-button link type="primary">查看</el-button> <el-button link type="primary">查看</el-button>
</template> </template>
<div v-for="(r, subIndex) in getContent($index).replies" :key="subIndex"> <div v-for="(r, subIndex) in getContent($index).replies" :key="subIndex">
<div>{{ r.formTitle }}</div>
<div>{{ r.contentTitle }}</div>
<div><h3>{{ r.formTitle }}</h3></div>
<div><h1>{{ r.contentTitle }}</h1></div>
<div>{{ r.content }}</div> <div>{{ r.content }}</div>
<div style="margin-bottom: 10px;"></div> <div style="margin-bottom: 10px;"></div>
</div> </div>
@ -146,9 +146,9 @@ const searchData = async () => {
} catch (error) { } catch (error) {
console.error('搜索失败', error); console.error('搜索失败', error);
} }
form.value.jwcode = "";
form.value.deptId = "";
form.value.shopId = "";
// form.value.jwcode = "";
// form.value.deptId = "";
// form.value.shopId = "";
} }
// //
const dept = ref([]); const dept = ref([]);
@ -209,6 +209,9 @@ const getContent = (index) => {
}; };
}; };
const exportData = async () => { const exportData = async () => {
if(!workdetailData.value){
ElMessage.warning('暂无数据可导出');
}
try { try {
const params = { const params = {
// form.valueid.value // form.valueid.value

563
work/src/views/WorksShowView.vue

@ -1,563 +0,0 @@
<script setup>
import { ref } from 'vue';
import ShowApi from '../api/ShowApi';
import { format } from 'date-fns';
import {useRouter} from "vue-router";
import {ElMessage} from "element-plus";
const router = useRouter()
//
const works = ref([]);
function loadWorks() {
ShowApi.getWorks().then(result => {
works.value = result.data;
console.log(works.value);
console.log(result.data)
works.value.forEach(work => {
let date = work.endData;
work.endData = format(new Date(date), 'yyyy-MM-dd');
});
})
}
loadWorks();
//
function writeWorks(id,sub){
if(sub >= 3){
ElMessage.error('每个作业可提交3次,您已提交3次。')
}else{
router.push({
path:`/doWork/${id}/${sub}`
})
}
}
</script>
<template>
<div class="container">
<div class="works">
<div class="work-header">
<img class="ketangzuoye" src="http://39.101.133.168:8857/LiveActivity/img/ketangzuoye.cc888815.png">
<img class="book"
src="https://img.js.design/assets/img/65f9235904fb00a3ea731672.png#dcda48ae8da37daeccd6583d45c7790b">
</div>
<div class="work-list">
<div class="list" v-for="work in works">
<div class="work-item">
<div class="work-name">
{{ work.name }}
</div>
<div class="work-content">
<div class="work-time">
<span class="deadline">截止时间{{ work.endData }}</span>
<!-- 作业提价状态 -->
<div v-if="work.submit == 0" class="work-status">未提交</div>
<div v-else class="work-status2">已提交</div>
</div>
<div class="work-bottem">
<span class="write" @click="writeWorks(work.groupId,work.submit)">写作业</span>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</template>
<style scoped>
.container {
width: 27%; /* 假设桌面布局的容器宽度为 80% */
margin: 0 auto; /* 居中对齐 */
}
body{
margin: 0;
}
.work-name {
opacity: 1;
/** 文本1 */
font-size: 1.5vw;
font-weight: 700;
letter-spacing: 0px;
color: rgba(53, 56, 112, 1);
text-align: left;
/*左对齐*/
vertical-align: top;
/* 这个属性在 Flex 容器中不起作用,将被移除 */
display: flex;
/* 启用 Flexbox 布局 */
align-items: center;
/* 垂直居中 */
height: 30%;
/* 设置高度,根据需要调整 */
width: 50%;
/* 如果需要,也可以设置宽度 */
}
.ketangzuoye {
margin-top: 2vh;
margin-left: 2vw;
width: 43%;
}
.book {
float: right;
margin-right: 1vw;
width: 30%;
}
/* 手机 */
@media (max-width: 768px) {
.container {
width: 100%;
margin: auto;
}
.works {
/* ../api/ShowApi
work\src\assets\bg@3x.png */
background-image: url('../assets/bg.png');
background-size: 100% 100%;
background-color: #8f98f6;
width: 100%;
min-height: 100vh;
position: relative;
margin: auto;
}
.work-list {
width: 95%;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
margin: auto;
}
.list {
display: flex;
justify-content: center;
align-items: center;
width: 97%;
height: 16vh;
opacity: 1;
border-radius: 10px;
background-color: rgba(255, 225, 174, 1);
margin-bottom: 3%;
}
.work-item {
width: 87%;
height: 63%;
padding: 10px;
position: relative;
background: linear-gradient(180deg, rgba(255, 255, 255, 1) 0%, rgba(250, 245, 235, 1) 100%);
border-radius: 10px;
border-radius: 10px;
}
.work-name {
opacity: 1;
/** 文本1 */
font-size: 4vw;
font-weight: 700;
letter-spacing: 0px;
color: rgba(53, 56, 112, 1);
text-align: left;
/*左对齐*/
vertical-align: top;
/* 这个属性在 Flex 容器中不起作用,将被移除 */
display: flex;
/* 启用 Flexbox 布局 */
align-items: center;
/* 垂直居中 */
height: 30%;
/* 设置高度,根据需要调整 */
width: 50%;
/* 如果需要,也可以设置宽度 */
}
.work-content {
width: 95%;
height: 35%;
position: absolute;
bottom: 10%;
display: flex;
}
.work-time {
position: absolute;
display: flex;
width: 70%;
bottom: 12%;
}
.deadline {
color: rgba(142, 142, 142, 1);
font-size: 3.6vw;
opacity: 1;
align-items: center;
padding-top: 0.5vw;
/* 水平居中 */
/* justify-content: center; */
}
.work-status {
font-size: 3.8vw;
display: inline-block;
background: rgba(53, 56, 112, 0.1);
padding: 1% 3.5%;
text-align: center;
color: #353870;
border-radius: 5px;
opacity: 2;
margin-left: 5px;
}
.work-status2 {
font-size: 3.8vw;
display: inline-block;
background: #ffe1ae;
padding: 1% 3.5%;
text-align: center;
color: #353870;
border-radius: 5px;
opacity: 2;
margin-left: 5px;
}
.work-bottem {
cursor: pointer;
display: flex;
position: absolute;
width: 28%;
height: 70%;
right: 0;
bottom: 2%;
opacity: 1;
border-radius: 50px;
background: linear-gradient(270deg, rgba(4, 15, 179, 1) 0%, rgba(120, 89, 255, 1) 100%);
border: 1px solid #a5e0f3;
justify-content: center;
/* 水平居中 */
align-items: center;
/* 垂直居中 */
text-align: center;
/* 确保文本在其容器内居中 */
}
.write {
opacity: 1;
/** 文本1 */
padding: auto;
font-size: 18px;
font-weight: 700;
letter-spacing: 0px;
line-height: 26.06px;
color: rgba(255, 255, 255, 1);
}
}
/* 平板 */
@media (min-width: 768px) and (max-width:1280px) {
.container {
width: 100%;
margin: auto;
}
.works {
/* ../api/ShowApi
work\src\assets\bg@3x.png */
background-image: url('../assets/bg@2x.png');
background-color: #8f98f6;
width: 100%;
min-height: 100vh;
position: relative;
margin: auto;
background-size: 100% 100%;
}
.work-list {
width: 95%;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
margin: auto;
}
.list {
display: flex;
justify-content: center;
align-items: center;
width: 97%;
height: 17vh;
opacity: 1;
border-radius: 10px;
background-color: rgba(255, 225, 174, 1);
margin-bottom: 3%;
}
.work-item {
width: 90%;
height: 70%;
padding: 10px;
position: relative;
background: linear-gradient(180deg, rgba(255, 255, 255, 1) 0%, rgba(250, 245, 235, 1) 100%);
border-radius: 10px;
border-radius: 10px;
}
.work-name {
opacity: 1;
/** 文本1 */
font-size: 1.6rem;
font-weight: 700;
letter-spacing: 0px;
color: rgba(53, 56, 112, 1);
text-align: left;
/*左对齐*/
vertical-align: top;
/* 这个属性在 Flex 容器中不起作用,将被移除 */
display: flex;
/* 启用 Flexbox 布局 */
align-items: center;
/* 垂直居中 */
height: 30%;
/* 设置高度,根据需要调整 */
width: 50%;
/* 如果需要,也可以设置宽度 */
}
.work-content {
width: 90%;
height: 35%;
position: absolute;
bottom: 10%;
display: flex;
}
.work-time {
position: absolute;
display: flex;
width: 70%;
bottom: 20%;
}
.deadline {
color: rgba(142, 142, 142, 1);
font-size: 14px;
opacity: 1;
}
.work-status {
display: inline-block;
background: rgba(53, 56, 112, 0.1);
padding: 0.5% 2%;
text-align: center;
color: #353870;
font-size: 1rem;
border-radius: 5px;
opacity: 2;
margin-left: 5px;
}
.work-status2 {
display: inline-block;
background: #ffe1ae;
padding: 0.5% 2%;
text-align: center;
color: #353870;
font-size: 1rem;
border-radius: 5px;
opacity: 2;
margin-left: 5px;
}
.work-bottem {
cursor: pointer;
display: flex;
position: absolute;
width: 25%;
height: 70%;
right: 0%;
bottom: 2%;
opacity: 1;
border-radius: 50px;
background: linear-gradient(270deg, rgba(4, 15, 179, 1) 0%, rgba(120, 89, 255, 1) 100%);
border: 1px solid #a5e0f3;
justify-content: center;
/* 水平居中 */
align-items: center;
/* 垂直居中 */
text-align: center;
/* 确保文本在其容器内居中 */
}
.write {
opacity: 1;
/** 文本1 */
padding: auto;
font-size: 1.125rem;
font-weight: 700;
letter-spacing: 0px;
line-height: 26.06px;
color: rgba(255, 255, 255, 1);
}
}
/* 电脑 */
@media (min-width: 1280px) {
.container {
width: 27%;
margin: auto;
}
.works {
/* ../api/ShowApi
work\src\assets\bg@3x.png */
background-image: url('../assets/bg@3x.png');
background-color: #8f98f6;
width: 100%;
min-height: 100vh;
position: relative;
margin: auto;
background-size: 100% 100%;
}
.work-name {
opacity: 1;
/** 文本1 */
font-size: 1.4vw;
font-weight: 700;
letter-spacing: 0px;
color: rgba(53, 56, 112, 1);
text-align: left;
/*左对齐*/
vertical-align: top;
/* 这个属性在 Flex 容器中不起作用,将被移除 */
display: flex;
/* 启用 Flexbox 布局 */
align-items: center;
/* 垂直居中 */
height: 30%;
/* 设置高度,根据需要调整 */
width: 70%;
}
.work-list {
width: 95%;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
margin: auto;
}
.list {
display: flex;
justify-content: center;
align-items: center;
width: 97%;
height: 17vh;
opacity: 1;
border-radius: 10px;
background-color: rgba(255, 225, 174, 1);
margin-bottom: 3%;
}
.work-item {
width: 90%;
height: 70%;
padding: 10px;
position: relative;
background: linear-gradient(180deg, rgba(255, 255, 255, 1) 0%, rgba(250, 245, 235, 1) 100%);
border-radius: 10px;
border-radius: 10px;
}
.work-content {
width: 90%;
height: 35%;
position: absolute;
bottom: 10%;
display: flex;
}
.work-time {
position: absolute;
display: flex;
width: 70%;
bottom: 15%;
}
.deadline {
color: rgba(142, 142, 142, 1);
font-size: 14px;
opacity: 1;
align-items: center;
padding-top: 0.2vw;
}
.work-status {
display: inline-block;
background: rgba(53, 56, 112, 0.1);
padding: 0.5% 2%;
text-align: center;
color: #353870;
font-size: 1rem;
border-radius: 5px;
opacity: 2;
margin-left: 5px;
}
.work-status2 {
display: inline-block;
background: #ffe1ae;
padding: 0.5% 2%;
text-align: center;
color: #353870;
font-size: 1rem;
border-radius: 5px;
opacity: 2;
margin-left: 5px;
}
.work-bottem {
cursor: pointer;
display: flex;
position: absolute;
width: 25%;
height: 70%;
right: 0%;
bottom: 2%;
opacity: 1;
border-radius: 50px;
background: linear-gradient(270deg, rgba(4, 15, 179, 1) 0%, rgba(120, 89, 255, 1) 100%);
border: 1px solid #a5e0f3;
justify-content: center;
/* 水平居中 */
align-items: center;
/* 垂直居中 */
text-align: center;
/* 确保文本在其容器内居中 */
}
.write {
opacity: 1;
/** 文本1 */
padding: auto;
font-size: 1.125rem;
font-weight: 700;
letter-spacing: 0px;
line-height: 26.06px;
color: rgba(255, 255, 255, 1);
}
}
.work-list{
margin-top: 12%;
}
</style>

2
work/vite.config.js

@ -16,7 +16,7 @@ export default defineConfig({
server: { server: {
proxy: { proxy: {
'/api': { '/api': {
target: 'http://192.168.8.191:8080',
target: 'http://192.168.9.19:8080',
changeOrigin: true, changeOrigin: true,
rewrite: (path) => path.replace(/^\/api/, '') rewrite: (path) => path.replace(/^\/api/, '')
}, },

Loading…
Cancel
Save