|
|
|
<% this.adminPage = 'classify'; %>
|
|
|
|
<% include admin_header %>
|
|
|
|
<style>
|
|
|
|
[v-cloak] {
|
|
|
|
display: none;
|
|
|
|
}
|
|
|
|
.current-classify{
|
|
|
|
margin-bottom: 20px;
|
|
|
|
}
|
|
|
|
.classify{
|
|
|
|
height:85%;
|
|
|
|
overflow: auto;
|
|
|
|
}
|
|
|
|
.ui.modal>.close {
|
|
|
|
top: 1.0535rem;
|
|
|
|
right: 1rem;
|
|
|
|
color: rgba(0, 0, 0, .87);
|
|
|
|
}
|
|
|
|
</style>
|
|
|
|
<div id="classify" v-cloak>
|
|
|
|
<div class="ui modal classify">
|
|
|
|
<i class="close icon"></i>
|
|
|
|
<div class="header">
|
|
|
|
{{calcModalTitle}}
|
|
|
|
</div>
|
|
|
|
<div class="content">
|
|
|
|
<div class="ui form">
|
|
|
|
<div class="field required" :class="{ error: classifyName.length > 20 }">
|
|
|
|
<label>练习阶段名称(20字以内)</label>
|
|
|
|
<input type="text" v-model="classifyName" placeholder="请输入分类名称">
|
|
|
|
</div>
|
|
|
|
<div class="field required" :class="{ error: classifyName.length > 100 }">
|
|
|
|
<label>练习阶段简介(100字以内)</label>
|
|
|
|
<input type="text" v-model="classifyIntro" placeholder="请输入分类简介">
|
|
|
|
</div>
|
|
|
|
<div class="field required" >
|
|
|
|
<label>练习阶段顺序</label>
|
|
|
|
<el-input-number disabled v-model="order" :min="1" :max="calcOrderMax" label="练习阶段顺序"></el-input-number>
|
|
|
|
</div>
|
|
|
|
<div class="field">
|
|
|
|
<label>当前练习阶段已经选择的题</label>
|
|
|
|
<el-tag @close="handleClose(item)" closable v-for="item in multipleSelection" style="margin-right:5px">#{{item.id}}{{item.title}}</el-tag>
|
|
|
|
</div>
|
|
|
|
<div class="field required" :class="{ error: multipleSelection.length === 0 }">
|
|
|
|
<label>题目选择(至少包含一道题)</label>
|
|
|
|
<el-table
|
|
|
|
ref="multipleTable"
|
|
|
|
:data="problemList"
|
|
|
|
tooltip-effect="dark"
|
|
|
|
style="width: 100%"
|
|
|
|
@select="handleSelectionChange"
|
|
|
|
>
|
|
|
|
<el-table-column
|
|
|
|
type="selection"
|
|
|
|
:selectable="disableCheckbox"
|
|
|
|
width="55">
|
|
|
|
</el-table-column>
|
|
|
|
<el-table-column
|
|
|
|
prop="id"
|
|
|
|
label="题目id">
|
|
|
|
</el-table-column>
|
|
|
|
<el-table-column
|
|
|
|
prop="title"
|
|
|
|
label="题目标题">
|
|
|
|
</el-table-column>
|
|
|
|
</el-table>
|
|
|
|
<el-pagination
|
|
|
|
@current-change="handlePageChange"
|
|
|
|
layout="prev, pager, next"
|
|
|
|
:current-page.sync="currentPage"
|
|
|
|
:total="problemCount">
|
|
|
|
</el-pagination>
|
|
|
|
</div>
|
|
|
|
<!-- <div is='problem-table' @getuserchoose="handleUserChoose" :userselectarray="multipleSelection" :disabledidarray="disabledId"></div>-->
|
|
|
|
<button class="ui button" @click="submitInfo">保存</button>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<div v-if="classifyArray.length === 0">
|
|
|
|
<div class="ui placeholder segment">
|
|
|
|
<div class="ui icon header">
|
|
|
|
<i class="sticky note icon"></i>
|
|
|
|
暂无练习阶段
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<div v-else>
|
|
|
|
<div class="current-classify">
|
|
|
|
<h4>目前练习阶段</h4>
|
|
|
|
<div class="ui cards">
|
|
|
|
<div class="card" v-for="item in classifyArray">
|
|
|
|
<div class="content">
|
|
|
|
<div class="header">{{item.name}}</div>
|
|
|
|
<div class="description">
|
|
|
|
{{item.intro}}
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<div class="ui bottom attached button" @click="show(item.id)">
|
|
|
|
<i class="add icon"></i>
|
|
|
|
编辑练习阶段信息
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<div class="ui labeled button" tabindex="0" @click="show()">
|
|
|
|
<div class="ui button">
|
|
|
|
<i class="plus icon"></i> 新增练习阶段
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
<link href="/cdnjs/element/element.css" rel="stylesheet">
|
|
|
|
<!-- 引入组件库 -->
|
|
|
|
<script src="/cdnjs/element/vue.min.js"></script>
|
|
|
|
<script src="/cdnjs/element/element-ui.min.js"></script>
|
|
|
|
|
|
|
|
<% include problem_table %>
|
|
|
|
<script>
|
|
|
|
new window.Vue({
|
|
|
|
el: '#classify',
|
|
|
|
data: {
|
|
|
|
problemIdArray: [],
|
|
|
|
order: 1,
|
|
|
|
classifyName: '',
|
|
|
|
classifyIntro: '',
|
|
|
|
classifyArray: [],
|
|
|
|
classifyId: -1,
|
|
|
|
loading: false,
|
|
|
|
problemList: [],
|
|
|
|
allproblemList: [],
|
|
|
|
usedProblemId: [],
|
|
|
|
multipleSelection: [],
|
|
|
|
problemCount: -1,
|
|
|
|
currentPage:1,
|
|
|
|
disabledId: [],
|
|
|
|
},
|
|
|
|
created: function() {
|
|
|
|
this.getClassifyInfo();
|
|
|
|
this.getCount();
|
|
|
|
},
|
|
|
|
methods: {
|
|
|
|
handleClose(tag) {
|
|
|
|
const deleteItem = this.multipleSelection.splice(this.multipleSelection.indexOf(tag), 1);
|
|
|
|
this.toggleSelection(deleteItem)
|
|
|
|
},
|
|
|
|
getCount: function(){
|
|
|
|
let that = this;
|
|
|
|
$.ajax({
|
|
|
|
url: '/api/pagination/allproblem',
|
|
|
|
type: 'GET',
|
|
|
|
success: function (data) {
|
|
|
|
that.problemCount = parseInt(data.problemInfo.length);
|
|
|
|
that.allproblemList = data.problemInfo;
|
|
|
|
},
|
|
|
|
error: function (XMLHttpRequest, textStatus, errorThrown) {
|
|
|
|
alert('创建失败');
|
|
|
|
}
|
|
|
|
})
|
|
|
|
},
|
|
|
|
disableCheckbox: function(row) {
|
|
|
|
return !this.disabledId.includes(row.id);
|
|
|
|
},
|
|
|
|
toggleSelection(rows) {
|
|
|
|
if (rows) {
|
|
|
|
rows.forEach(row => {
|
|
|
|
this.$refs.multipleTable.toggleRowSelection(row);
|
|
|
|
});
|
|
|
|
} else {
|
|
|
|
this.$refs.multipleTable.clearSelection();
|
|
|
|
}
|
|
|
|
},
|
|
|
|
handlePageChange(page) {
|
|
|
|
this.selectProblem(this.multipleSelection);
|
|
|
|
this.getProblemPagination(page);
|
|
|
|
},
|
|
|
|
getProblemPagination(page) {
|
|
|
|
let that = this;
|
|
|
|
this.problemList = this.allproblemList.slice((page - 1)*10, (page - 1)*10+10);
|
|
|
|
this.$nextTick(function(){
|
|
|
|
that.toggleSelection(that.multipleSelection);
|
|
|
|
})
|
|
|
|
},
|
|
|
|
handleSelectionChange(val, row) {
|
|
|
|
console.log(val);
|
|
|
|
const multipleSelectionId = this.multipleSelection.map(item => item.id);
|
|
|
|
if (multipleSelectionId.includes(row.id)) {
|
|
|
|
this.multipleSelection.splice(this.multipleSelection.indexOf(row), 1)
|
|
|
|
} else {
|
|
|
|
this.multipleSelection.push(row);
|
|
|
|
}
|
|
|
|
},
|
|
|
|
getClassifyInfo: function() {
|
|
|
|
let that = this;
|
|
|
|
$.ajax({
|
|
|
|
url: '/api/practice/all',
|
|
|
|
type: 'GET',
|
|
|
|
success: function (data) {
|
|
|
|
that.classifyArray = data.result;
|
|
|
|
that.usedProblemId = data.problem.map(function(item){return item.p_id});
|
|
|
|
},
|
|
|
|
error: function (XMLHttpRequest, textStatus, errorThrown) {
|
|
|
|
alert('查询失败');
|
|
|
|
}
|
|
|
|
});
|
|
|
|
},
|
|
|
|
resetModal: function() {
|
|
|
|
this.classifyName = '';
|
|
|
|
this.classifyIntro = '';
|
|
|
|
// this.problemIdArray = [];
|
|
|
|
this.classifyId = -1;
|
|
|
|
this.order = this.calcOrderMax;
|
|
|
|
},
|
|
|
|
selectProblem: function(array) {
|
|
|
|
this.toggleSelection(array)
|
|
|
|
},
|
|
|
|
getClassifyInfos: function(id){
|
|
|
|
let that = this;
|
|
|
|
if (id !== -1) {
|
|
|
|
$.ajax({
|
|
|
|
url: `/api/practice/classify/${id}`,
|
|
|
|
type: 'GET',
|
|
|
|
success: function (data) {
|
|
|
|
if (!data.error_code) {
|
|
|
|
const {classifyInfo: {id, intro, name, order}, problem} = data;
|
|
|
|
that.classifyName = name;
|
|
|
|
that.classifyIntro = intro;
|
|
|
|
that.problemIdArray = that.allproblemList.filter(function(problemItem){
|
|
|
|
return problem.includes(problemItem.id)
|
|
|
|
});
|
|
|
|
const currentIdArray = that.problemIdArray.map((function(item){
|
|
|
|
return item.id;
|
|
|
|
}));
|
|
|
|
function findDifference(source, target){
|
|
|
|
return target.filter(function(item){
|
|
|
|
return !source.includes(item);
|
|
|
|
})
|
|
|
|
}
|
|
|
|
that.disabledId = findDifference(currentIdArray, that.usedProblemId);
|
|
|
|
that.multipleSelection = that.problemIdArray;
|
|
|
|
that.getProblemPagination(1);
|
|
|
|
that.order = order;
|
|
|
|
}
|
|
|
|
},
|
|
|
|
error: function (XMLHttpRequest, textStatus, errorThrown) {
|
|
|
|
alert('创建失败');
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
},
|
|
|
|
show: function(id){
|
|
|
|
let that = this;
|
|
|
|
if (id) {
|
|
|
|
this.classifyId = id;
|
|
|
|
this.getClassifyInfos(id);
|
|
|
|
this.currentPage = 1;
|
|
|
|
} else {
|
|
|
|
this.resetModal();
|
|
|
|
}
|
|
|
|
$('.ui.modal.classify')
|
|
|
|
.modal('show')
|
|
|
|
},
|
|
|
|
checkStringLength: function(string, maxLen) {
|
|
|
|
return string.length > 0 && string.length <= maxLen;
|
|
|
|
},
|
|
|
|
submitInfo: function() {
|
|
|
|
let that = this;
|
|
|
|
let name = this.classifyName;
|
|
|
|
let intro = this.classifyIntro;
|
|
|
|
if(this.checkStringLength(name, 20) && this.checkStringLength(intro, 100) && this.multipleSelection.length > 0) {
|
|
|
|
const obj = {
|
|
|
|
name: this.classifyName,
|
|
|
|
intro: this.classifyIntro,
|
|
|
|
order: this.order,
|
|
|
|
problemIdArray: this.multipleSelection.map(item=>item.id)
|
|
|
|
}
|
|
|
|
if (this.classifyId === -1) {
|
|
|
|
$.ajax({
|
|
|
|
url: '/api/practice/create',
|
|
|
|
type: 'POST',
|
|
|
|
async: true,
|
|
|
|
data: obj,
|
|
|
|
success: function (data) {
|
|
|
|
if (data.error_code) {
|
|
|
|
alert('创建失败');
|
|
|
|
that.resetModal();
|
|
|
|
} else {
|
|
|
|
alert('添加成功');
|
|
|
|
that.resetModal();
|
|
|
|
$('.ui.modal.classify')
|
|
|
|
.modal('hide')
|
|
|
|
that.getClassifyInfo();
|
|
|
|
}
|
|
|
|
},
|
|
|
|
error: function (XMLHttpRequest, textStatus, errorThrown) {
|
|
|
|
alert('创建失败');
|
|
|
|
}
|
|
|
|
});
|
|
|
|
} else {
|
|
|
|
$.ajax({
|
|
|
|
url: `/api/practice/classify/update/${that.classifyId}`,
|
|
|
|
type: 'PUT',
|
|
|
|
async: true,
|
|
|
|
data: obj,
|
|
|
|
success: function (data) {
|
|
|
|
if (data.error_code) {
|
|
|
|
alert('更新失败');
|
|
|
|
} else {
|
|
|
|
alert('更新成功');
|
|
|
|
that.resetModal();
|
|
|
|
$('.ui.modal.classify')
|
|
|
|
.modal('hide')
|
|
|
|
that.getClassifyInfo();
|
|
|
|
}
|
|
|
|
},
|
|
|
|
error: function (XMLHttpRequest, textStatus, errorThrown) {
|
|
|
|
alert('更新时发生错误');
|
|
|
|
}
|
|
|
|
});
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
},
|
|
|
|
computed: {
|
|
|
|
calcModalTitle: function(){
|
|
|
|
if (this.classifyId === -1) {
|
|
|
|
return '新增练习阶段';
|
|
|
|
} else {
|
|
|
|
return '编辑练习阶段'
|
|
|
|
}
|
|
|
|
},
|
|
|
|
calcOrderMax: function() {
|
|
|
|
if (this.classifyId === -1) {
|
|
|
|
return this.classifyArray.length + 1;
|
|
|
|
} else {
|
|
|
|
return this.classifyArray.length
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
})
|
|
|
|
</script>
|
|
|
|
<% include admin_footer %>
|