Browse Source

激活码功能完善

master
zhouyulong 16 hours ago
parent
commit
49b24d1957
  1. 4710
      pnpm-lock.yaml
  2. 44
      src/api/mmxt/mmxtMeiyuTextbookActivate.js
  3. 63
      src/api/mmxt/mmxtMeiyuTextbookActivateBatch.js
  4. 44
      src/api/mmxt/mmxtMeiyuTextbookActivateLog.js
  5. 308
      src/assets/styles/mmxt.scss
  6. 7
      src/utils/mitt.js
  7. 228
      src/utils/mmxt.js
  8. 289
      src/views/mmxt/mmxtMeiyuTextbookActivate/components/detailsdaing.vue
  9. 337
      src/views/mmxt/mmxtMeiyuTextbookActivate/index.vue

4710
pnpm-lock.yaml

File diff suppressed because it is too large

44
src/api/mmxt/mmxtMeiyuTextbookActivate.js

@ -0,0 +1,44 @@
import request from '@/utils/request'
// 查询美美学堂智慧美育教材学习卡激活码列表
export function listMmxtMeiyuTextbookActivate(query) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivate/list',
method: 'get',
params: query
})
}
// 查询美美学堂智慧美育教材学习卡激活码详细
export function getMmxtMeiyuTextbookActivate(recordId) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivate/' + recordId,
method: 'get'
})
}
// 新增美美学堂智慧美育教材学习卡激活码
export function addMmxtMeiyuTextbookActivate(data) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivate',
method: 'post',
data: data
})
}
// 修改美美学堂智慧美育教材学习卡激活码
export function updateMmxtMeiyuTextbookActivate(data) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivate',
method: 'put',
data: data
})
}
// 删除美美学堂智慧美育教材学习卡激活码
export function delMmxtMeiyuTextbookActivate(recordId) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivate/' + recordId,
method: 'delete'
})
}

63
src/api/mmxt/mmxtMeiyuTextbookActivateBatch.js

@ -0,0 +1,63 @@
import request from '@/utils/request'
// 查询美美学堂智慧美育教材学习卡激活批次列表
export function listMmxtMeiyuTextbookActivateBatch(query) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateBatch/list',
method: 'get',
params: query
})
}
// 查询美美学堂智慧美育教材学习卡激活批次详细
export function getMmxtMeiyuTextbookActivateBatch(batchId) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateBatch/' + batchId,
method: 'get'
})
}
// 新增美美学堂智慧美育教材学习卡激活批次
export function addMmxtMeiyuTextbookActivateBatch(data) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateBatch/batchInsertTextbookActivate',
method: 'post',
data: data
})
}
// 修改美美学堂智慧美育教材学习卡激活批次
export function updateMmxtMeiyuTextbookActivateBatch(data) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateBatch',
method: 'put',
data: data
})
}
// 删除美美学堂智慧美育教材学习卡激活批次
export function delMmxtMeiyuTextbookActivateBatch(batchId) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateBatch/' + batchId,
method: 'delete'
})
}
// 查询美美学堂智慧美育区域简易列表
export function selectMmxtMeiyuRegionByEasy(query) {
return request({
url: '/mmxt/mmxtMeiyuRegion/selectMmxtMeiyuRegionByEasy',
method: 'get',
params: query
})
}
// 查询美美学堂智慧美育教材简易列表
export function selectTextbookEasy(query) {
return request({
url: '/mmxt/mmxtMeiyuTextbook/selectTextbookEasy',
method: 'get',
params: query
})
}

44
src/api/mmxt/mmxtMeiyuTextbookActivateLog.js

@ -0,0 +1,44 @@
import request from '@/utils/request'
// 查询美美学堂智慧美育教材学习卡激活码日志列表
export function listMmxtMeiyuTextbookActivateLog(query) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivate/selectActivationList',
method: 'get',
params: query
})
}
// 查询美美学堂智慧美育教材学习卡激活码日志详细
export function getMmxtMeiyuTextbookActivateLog(logId) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateLog/' + logId,
method: 'get'
})
}
// 新增美美学堂智慧美育教材学习卡激活码日志
export function addMmxtMeiyuTextbookActivateLog(data) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateLog',
method: 'post',
data: data
})
}
// 修改美美学堂智慧美育教材学习卡激活码日志
export function updateMmxtMeiyuTextbookActivateLog(data) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateLog',
method: 'put',
data: data
})
}
// 删除美美学堂智慧美育教材学习卡激活码日志
export function delMmxtMeiyuTextbookActivateLog(logId) {
return request({
url: '/mmxt/mmxtMeiyuTextbookActivateLog/' + logId,
method: 'delete'
})
}

308
src/assets/styles/mmxt.scss

@ -0,0 +1,308 @@
/**
* 通用css样式布局处理
* Copyright (c) 2019 mmxt
*/
/** 基础通用 **/
.pt5 {
padding-top: 5px;
}
.pr5 {
padding-right: 5px;
}
.pb5 {
padding-bottom: 5px;
}
.mt5 {
margin-top: 5px;
}
.mr5 {
margin-right: 5px;
}
.mb5 {
margin-bottom: 5px;
}
.mb8 {
margin-bottom: 8px;
}
.ml5 {
margin-left: 5px;
}
.mt10 {
margin-top: 10px;
}
.mr10 {
margin-right: 10px;
}
.mb10 {
margin-bottom: 10px;
}
.ml10 {
margin-left: 10px;
}
.mt20 {
margin-top: 20px;
}
.mr20 {
margin-right: 20px;
}
.mb20 {
margin-bottom: 20px;
}
.ml20 {
margin-left: 20px;
}
.h1, .h2, .h3, .h4, .h5, .h6, h1, h2, h3, h4, h5, h6 {
font-family: inherit;
font-weight: 500;
line-height: 1.1;
color: inherit;
}
.el-form--inline {
.el-form-item {
.el-input, .el-cascader, .el-select, .el-autocomplete {
width: 200px;
}
}
}
.el-form .el-form-item__label {
font-weight: 700;
}
.el-dialog:not(.is-fullscreen) {
margin-top: 6vh !important;
}
.el-dialog.scrollbar .el-dialog__body {
overflow: auto;
overflow-x: hidden;
max-height: 70vh;
padding: 10px 20px 0;
}
.el-table {
.el-table__header-wrapper, .el-table__fixed-header-wrapper {
th {
word-break: break-word;
background-color: #f8f8f9 !important;
color: #515a6e;
height: 40px !important;
font-size: 13px;
}
}
.el-table__body-wrapper {
.el-button [class*="el-icon-"] + span {
margin-left: 1px;
}
}
}
/** 表单布局 **/
.form-header {
font-size:15px;
color:#6379bb;
border-bottom:1px solid #ddd;
margin:8px 10px 25px 10px;
padding-bottom:5px
}
/** 表格布局 **/
.pagination-container {
display: flex;
justify-content: flex-end;
margin-top: 20px;
background-color: transparent !important;
}
/* 弹窗中的分页器 */
.el-dialog .pagination-container {
position: static !important;
margin: 10px 0 0 0;
padding: 0 !important;
.el-pagination {
position: static;
}
}
/* 移动端适配 */
@media (max-width: 768px) {
.pagination-container {
.el-pagination {
> .el-pagination__jump {
display: none !important;
}
> .el-pagination__sizes {
display: none !important;
}
}
}
}
/* tree border */
.tree-border {
margin-top: 5px;
border: 1px solid var(--el-border-color-light, #e5e6e7);
background: var(--el-bg-color, #FFFFFF) none;
border-radius:4px;
width: 100%;
}
.el-table .fixed-width .el-button--small {
padding-left: 0;
padding-right: 0;
width: inherit;
}
/* horizontal el menu */
.el-menu--horizontal .el-menu-item .svg-icon + span,
.el-menu--horizontal .el-sub-menu__title .svg-icon + span {
margin-left: 3px;
}
.el-menu--horizontal .el-menu--popup {
min-width: 120px !important;
}
/** 表格更多操作下拉样式 */
.el-table .el-dropdown-link {
cursor: pointer;
color: #409EFF;
margin-left: 10px;
}
.el-table .el-dropdown, .el-icon-arrow-down {
font-size: 12px;
}
.el-tree-node__content > .el-checkbox {
margin-right: 8px;
}
.list-group-striped > .list-group-item {
border-left: 0;
border-right: 0;
border-radius: 0;
padding-left: 0;
padding-right: 0;
}
.list-group {
padding-left: 0px;
list-style: none;
}
.list-group-item {
border-bottom: 1px solid #e7eaec;
border-top: 1px solid #e7eaec;
margin-bottom: -1px;
padding: 11px 0px;
font-size: 13px;
}
.pull-right {
float: right !important;
}
.el-card__header {
padding: 14px 15px 7px !important;
min-height: 40px;
}
.el-card__body {
padding: 15px 20px 20px 20px !important;
}
.card-box {
margin-bottom: 10px;
}
/* button color */
.el-button--cyan.is-active,
.el-button--cyan:active {
background: #20B2AA;
border-color: #20B2AA;
color: #FFFFFF;
}
.el-button--cyan:focus,
.el-button--cyan:hover {
background: #48D1CC;
border-color: #48D1CC;
color: #FFFFFF;
}
.el-button--cyan {
background-color: #20B2AA;
border-color: #20B2AA;
color: #FFFFFF;
}
/* text color */
.text-navy {
color: #1ab394;
}
.text-primary {
color: inherit;
}
.text-success {
color: #1c84c6;
}
.text-info {
color: #23c6c8;
}
.text-warning {
color: #f8ac59;
}
.text-danger {
color: #ed5565;
}
.text-muted {
color: #888888;
}
/* image */
.img-circle {
border-radius: 50%;
}
.img-lg {
width: 120px;
height: 120px;
}
.avatar-upload-preview {
position: absolute;
top: 50%;
transform: translate(50%, -50%);
width: 200px;
height: 200px;
border-radius: 50%;
box-shadow: 0 0 4px #ccc;
overflow: hidden;
}
/* 拖拽列样式 */
.sortable-ghost{
opacity: .8;
color: #fff!important;
background: #42b983!important;
}
/* 表格右侧工具栏样式 */
.top-right-btn {
margin-left: auto;
}
/* 分割面板样式 */
.splitpanes.default-theme .splitpanes__pane {
background-color: var(--splitpanes-default-bg) !important;
}

7
src/utils/mitt.js

@ -0,0 +1,7 @@
import mitt from 'mitt';
const emitter = mitt();
export default emitter;

228
src/utils/mmxt.js

@ -0,0 +1,228 @@
/**
* 通用js方法封装处理
* Copyright (c) 2019 mmxt
*/
// 日期格式化
export function parseTime(time, pattern) {
if (arguments.length === 0 || !time) {
return null
}
const format = pattern || '{y}-{m}-{d} {h}:{i}:{s}'
let date
if (typeof time === 'object') {
date = time
} else {
if ((typeof time === 'string') && (/^[0-9]+$/.test(time))) {
time = parseInt(time)
} else if (typeof time === 'string') {
time = time.replace(new RegExp(/-/gm), '/').replace('T', ' ').replace(new RegExp(/\.[\d]{3}/gm), '')
}
if ((typeof time === 'number') && (time.toString().length === 10)) {
time = time * 1000
}
date = new Date(time)
}
const formatObj = {
y: date.getFullYear(),
m: date.getMonth() + 1,
d: date.getDate(),
h: date.getHours(),
i: date.getMinutes(),
s: date.getSeconds(),
a: date.getDay()
}
const time_str = format.replace(/{(y|m|d|h|i|s|a)+}/g, (result, key) => {
let value = formatObj[key]
// Note: getDay() returns 0 on Sunday
if (key === 'a') { return ['日', '一', '二', '三', '四', '五', '六'][value] }
if (result.length > 0 && value < 10) {
value = '0' + value
}
return value || 0
})
return time_str
}
// 表单重置
export function resetForm(refName) {
if (this.$refs[refName]) {
this.$refs[refName].resetFields()
}
}
// 添加日期范围
export function addDateRange(params, dateRange, propName) {
let search = params
search.params = typeof (search.params) === 'object' && search.params !== null && !Array.isArray(search.params) ? search.params : {}
dateRange = Array.isArray(dateRange) ? dateRange : []
if (typeof (propName) === 'undefined') {
search.params['beginTime'] = dateRange[0]
search.params['endTime'] = dateRange[1]
} else {
search.params['begin' + propName] = dateRange[0]
search.params['end' + propName] = dateRange[1]
}
return search
}
// 回显数据字典
export function selectDictLabel(datas, value) {
if (value === undefined) {
return ""
}
var actions = []
Object.keys(datas).some((key) => {
if (datas[key].value == ('' + value)) {
actions.push(datas[key].label)
return true
}
})
if (actions.length === 0) {
actions.push(value)
}
return actions.join('')
}
// 回显数据字典(字符串、数组)
export function selectDictLabels(datas, value, separator) {
if (value === undefined || value.length === 0) {
return ""
}
if (Array.isArray(value)) {
value = value.join(",")
}
var actions = []
var currentSeparator = undefined === separator ? "," : separator
var temp = value.split(currentSeparator)
Object.keys(value.split(currentSeparator)).some((val) => {
var match = false
Object.keys(datas).some((key) => {
if (datas[key].value == ('' + temp[val])) {
actions.push(datas[key].label + currentSeparator)
match = true
}
})
if (!match) {
actions.push(temp[val] + currentSeparator)
}
})
return actions.join('').substring(0, actions.join('').length - 1)
}
// 字符串格式化(%s )
export function sprintf(str) {
var args = arguments, flag = true, i = 1
str = str.replace(/%s/g, function () {
var arg = args[i++]
if (typeof arg === 'undefined') {
flag = false
return ''
}
return arg
})
return flag ? str : ''
}
// 转换字符串,undefined,null等转化为""
export function parseStrEmpty(str) {
if (!str || str == "undefined" || str == "null") {
return ""
}
return str
}
// 数据合并
export function mergeRecursive(source, target) {
for (var p in target) {
try {
if (target[p].constructor == Object) {
source[p] = mergeRecursive(source[p], target[p])
} else {
source[p] = target[p]
}
} catch (e) {
source[p] = target[p]
}
}
return source
}
/**
* 构造树型结构数据
* @param {*} data 数据源
* @param {*} id id字段 默认 'id'
* @param {*} parentId 父节点字段 默认 'parentId'
* @param {*} children 孩子节点字段 默认 'children'
*/
export function handleTree(data, id, parentId, children) {
let config = {
id: id || 'id',
parentId: parentId || 'parentId',
childrenList: children || 'children'
}
var childrenListMap = {}
var tree = []
for (let d of data) {
let id = d[config.id]
childrenListMap[id] = d
if (!d[config.childrenList]) {
d[config.childrenList] = []
}
}
for (let d of data) {
let parentId = d[config.parentId]
let parentObj = childrenListMap[parentId]
if (!parentObj) {
tree.push(d)
} else {
parentObj[config.childrenList].push(d)
}
}
return tree
}
/**
* 参数处理
* @param {*} params 参数
*/
export function tansParams(params) {
let result = ''
for (const propName of Object.keys(params)) {
const value = params[propName]
var part = encodeURIComponent(propName) + "="
if (value !== null && value !== "" && typeof (value) !== "undefined") {
if (typeof value === 'object') {
for (const key of Object.keys(value)) {
if (value[key] !== null && value[key] !== "" && typeof (value[key]) !== 'undefined') {
let params = propName + '[' + key + ']'
var subPart = encodeURIComponent(params) + "="
result += subPart + encodeURIComponent(value[key]) + "&"
}
}
} else {
result += part + encodeURIComponent(value) + "&"
}
}
}
return result
}
// 返回项目路径
export function getNormalPath(p) {
if (p.length === 0 || !p || p == 'undefined') {
return p
}
let res = p.replace('//', '/')
if (res[res.length - 1] === '/') {
return res.slice(0, res.length - 1)
}
return res
}
// 验证是否为blob格式
export function blobValidate(data) {
return data.type !== 'application/json'
}

289
src/views/mmxt/mmxtMeiyuTextbookActivate/components/detailsdaing.vue

@ -0,0 +1,289 @@
<template>
<div>
<el-dialog :close-on-click-modal="false" class="padding20" v-model="dialogVisible" :title="title"
width="1200px">
<div class="app-container">
<el-form :model="queryParams" ref="queryRef" :inline="true" v-show="showSearch" label-width="68px">
<el-form-item v-if="queryParams.type == 0" label="学生名称" prop="studentName">
<el-input class="input150" v-model="queryParams.studentName" placeholder="请输入学生名称" clearable
@keyup.enter="handleQuery" />
</el-form-item>
<el-form-item label="激活码" prop="activateCode">
<el-input class="input150" v-model="queryParams.activateCode" placeholder="请输入激活码" clearable
@keyup.enter="handleQuery" />
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
<el-row :gutter="10" class="mb8">
<el-col :span="1.5" v-if="queryParams.type == 1">
<el-button type="danger" plain icon="Delete" :disabled="multiple"
@click="handleDelete">删除</el-button>
</el-col>
<el-col :span="1.5">
<el-button type="warning" plain icon="Download" @click="handleExport">导出</el-button>
</el-col>
<right-toolbar v-model:showSearch="showSearch" @queryTable="getList"></right-toolbar>
</el-row>
<el-table v-loading="loading" :data="mmxtMeiyuTextbookActivateLogList"
@selection-change="handleSelectionChange">
<el-table-column type="selection" width="55" align="center" />
<el-table-column label="序号" width="50" align="center">
<template #default="scope">
<span>{{
(queryParams.pageNum - 1) * queryParams.pageSize + scope.$index + 1
}}</span>
</template>
</el-table-column>
<el-table-column v-if="queryParams.type == 0" label="学生名称" align="center" prop="studentName" />
<el-table-column label="激活码" align="center" prop="activateCode" />
<el-table-column label="二维码" align="center" prop="qrCode">
<template #default="scope">
<div class="flexcenter">
<ImagePreview width="40px" height="40px" :src="scope.row.qrCode">
</ImagePreview>
</div>
</template>
</el-table-column>
<el-table-column v-if="queryParams.type == 0" label="IP地址" align="center" prop="ipaddr" />
<el-table-column v-if="queryParams.type == 0" label="浏览器类型" align="center" prop="browser" />
<el-table-column v-if="queryParams.type == 0" label="操作系统" align="center" prop="os" />
<el-table-column v-if="queryParams.type == 0" label="激活时间" align="center" prop="logTime"
width="180">
<template #default="scope">
<span>{{ parseTime(scope.row.logTime, '{y}-{m}-{d}') }}</span>
</template>
</el-table-column>
<el-table-column v-if="queryParams.type == 1" label="操作" align="center"
class-name="small-padding fixed-width">
<template #default="scope">
<el-button link type="primary" icon="Delete" @click="handleDelete(scope.row)">删除</el-button>
</template>
</el-table-column>
</el-table>
<pagination v-show="total>0" :total="total" v-model:page="queryParams.pageNum"
v-model:limit="queryParams.pageSize" @pagination="getList" />
</div>
<template #footer>
<div class="dialog-footer">
<!-- <el-button type="primary" @click="submitForm">确定</el-button> -->
<el-button @click="dialogVisible = false">取消</el-button>
</div>
</template>
</el-dialog>
</div>
</template>
<script setup name="yshzCompetitionTypediang">
import { listMmxtMeiyuTextbookActivateLog, getMmxtMeiyuTextbookActivateLog, delMmxtMeiyuTextbookActivateLog, addMmxtMeiyuTextbookActivateLog, updateMmxtMeiyuTextbookActivateLog } from "@/api/mmxt/mmxtMeiyuTextbookActivateLog"
import { listMmxtMeiyuTextbookActivate, getMmxtMeiyuTextbookActivate, delMmxtMeiyuTextbookActivate, addMmxtMeiyuTextbookActivate, updateMmxtMeiyuTextbookActivate } from "@/api/mmxt/mmxtMeiyuTextbookActivate"
import { selectTextbookEasy } from "@/api/mmxt/mmxtMeiyuTextbookActivateBatch"
import emitter from '@/utils/mitt';
const { proxy } = getCurrentInstance()
const dialogVisible = ref(false)
const yshzTextbookList = ref([])
const mmxtMeiyuTextbookActivateLogList = ref([])
const open = ref(false)
const loading = ref(true)
const showSearch = ref(true)
const ids = ref([])
const single = ref(true)
const multiple = ref(true)
const total = ref(0)
const title = ref("")
const data = reactive({
form: {},
queryParams: {
pageNum: 1,
pageSize: 10,
studentId: null,
textbookId: null,
activateCode: null,
ipaddr: null,
browser: null,
os: null,
logTime: null
},
rules: {}
})
const { queryParams, form, rules } = toRefs(data)
/** 查询美美学堂智慧美育教材学习卡激活码日志列表 */
function getList() {
loading.value = true
if (queryParams.value.type == 0) {
listMmxtMeiyuTextbookActivateLog(queryParams.value).then(response => {
mmxtMeiyuTextbookActivateLogList.value = response.rows
total.value = response.total
loading.value = false
})
} else {
listMmxtMeiyuTextbookActivate(queryParams.value).then(response => {
mmxtMeiyuTextbookActivateLogList.value = response.rows
total.value = response.total
loading.value = false
})
}
}
//
function cancel() {
open.value = false
reset()
}
//
function reset() {
form.value = {
logId: null,
studentId: null,
textbookId: null,
activateCode: null,
ipaddr: null,
browser: null,
os: null,
logTime: null
}
proxy.resetForm("mmxtMeiyuTextbookActivateLogRef")
}
/** 搜索按钮操作 */
function handleQuery() {
queryParams.value.pageNum = 1
getList()
}
/** 重置按钮操作 */
function resetQuery() {
proxy.resetForm("queryRef")
handleQuery()
}
//
function handleSelectionChange(selection) {
if (queryParams.value.type == 0) {
ids.value = selection.map(item => item.logId)
} else {
ids.value = selection.map(item => item.recordId)
}
single.value = selection.length != 1
multiple.value = !selection.length
}
/** 新增按钮操作 */
function handleAdd() {
reset()
open.value = true
}
/** 修改按钮操作 */
function handleUpdate(row) {
reset()
const _logId = row.logId || ids.value
getMmxtMeiyuTextbookActivateLog(_logId).then(response => {
form.value = response.data
open.value = true
})
}
/** 提交按钮 */
function submitForm() {
proxy.$refs["mmxtMeiyuTextbookActivateLogRef"].validate(valid => {
if (valid) {
if (form.value.logId != null) {
updateMmxtMeiyuTextbookActivateLog(form.value).then(response => {
proxy.$modal.msgSuccess("修改成功")
open.value = false
getList()
})
} else {
addMmxtMeiyuTextbookActivateLog(form.value).then(response => {
proxy.$modal.msgSuccess("新增成功")
open.value = false
getList()
})
}
}
})
}
/** 删除按钮操作 */
function handleDelete(row) {
if (queryParams.value.type == 0) {
const _logIds = row.logId || ids.value
proxy.$modal.confirm('是否确认删除激活码日志编号为"' + _logIds + '"的数据项?').then(function () {
return delMmxtMeiyuTextbookActivateLog(_logIds)
}).then(() => {
getList()
proxy.$modal.msgSuccess("删除成功")
}).catch(() => { })
} else {
const _logIds = row.recordId || ids.value
proxy.$modal.confirm('是否确认删除激活码编号为"' + _logIds + '"的数据项?').then(function () {
return delMmxtMeiyuTextbookActivate(_logIds)
}).then(() => {
getList()
emitter.emit('numberReflashlist', true);
proxy.$modal.msgSuccess("删除成功")
}).catch(() => { })
}
}
/** 导出按钮操作 */
function handleExport() {
if (queryParams.value.type == 0) {
proxy.download('mmxt/mmxtMeiyuTextbookActivate/exportActivate', {
...queryParams.value
}, `mmxtMeiyuTextbookActivate_${new Date().getTime()}.xlsx`)
} else {
proxy.download('mmxt/mmxtMeiyuTextbookActivate/export', {
...queryParams.value
}, `mmxtMeiyuTextbookActivateLog_${new Date().getTime()}.xlsx`)
}
}
function getlistYshztTextbook() {
selectTextbookEasy().then(response => {
yshzTextbookList.value = response.data.map(item => ({ label: item.textbookName, value: item.textbookId }))
})
}
//
const opens = (batchId, type) => {
queryParams.value.batchId = batchId
queryParams.value.type = type
dialogVisible.value = true
if (type == 0) {
title.value = "激活码日志"
} else {
title.value = "激活码列表"
}
getlistYshztTextbook()
getList()
}
defineExpose({
opens
})
</script>
<style lang="scss" scoped>
:deep(.pagination-container .el-pagination) {
right: 20px;
}
.input150 {
width: 150px;
}
</style>

337
src/views/mmxt/mmxtMeiyuTextbookActivate/index.vue

@ -0,0 +1,337 @@
<template>
<div class="app-container">
<el-form :model="queryParams" ref="queryRef" :inline="true" v-show="showSearch" label-width="68px">
<el-form-item label="批次" prop="batchName">
<el-input class="input150" v-model="queryParams.batchName" placeholder="请输入批次" clearable
@keyup.enter="handleQuery" />
</el-form-item>
<el-form-item label="地域名称" prop="regionId">
<el-tree-select style="width: 180px;" v-model="queryParams.regionId" :data="yshzRegionOptions"
:props="{ value: 'regionId', label: 'regionName', children: 'children' }" value-key="id"
placeholder="请选择地域" check-strictly />
</el-form-item>
<el-form-item>
<el-button type="primary" icon="Search" @click="handleQuery">搜索</el-button>
<el-button icon="Refresh" @click="resetQuery">重置</el-button>
</el-form-item>
</el-form>
<el-row :gutter="10" class="mb8">
<el-col :span="1.5">
<el-button type="primary" plain icon="Plus" @click="handleAdd"
v-hasPermi="['mmxt:mmxtMeiyuTextbookActivateBatch:add']">新增</el-button>
</el-col>
<el-col :span="1.5">
<el-button type="success" plain icon="Edit" :disabled="single" @click="handleUpdate"
v-hasPermi="['mmxt:mmxtMeiyuTextbookActivateBatch:edit']">修改</el-button>
</el-col>
<el-col :span="1.5">
<el-button type="danger" plain icon="Delete" :disabled="multiple" @click="handleDelete"
v-hasPermi="['mmxt:mmxtMeiyuTextbookActivateBatch:remove']">删除</el-button>
</el-col>
<el-col :span="1.5">
<el-button type="warning" plain icon="Download" @click="handleExport"
v-hasPermi="['mmxt:mmxtMeiyuTextbookActivateBatch:export']">导出</el-button>
</el-col>
<right-toolbar v-model:showSearch="showSearch" @queryTable="getList"></right-toolbar>
</el-row>
<el-table v-loading="loading" :data="mmxtMeiyuTextbookActivateList" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="55" align="center" />
<el-table-column label="序号" width="50" align="center">
<template #default="scope">
<span>{{
(queryParams.pageNum - 1) * queryParams.pageSize + scope.$index + 1
}}</span>
</template>
</el-table-column>
<el-table-column width="150" label="批次" align="center" prop="batchName" />
<el-table-column label="地域名称" align="center" prop="regionAddr" />
<el-table-column width="150" label="已激活数量" align="center" prop="activationCount">
<template #default="scope">
<span @click="todetails(scope.row,0)" class="viewspan">{{scope.row.activationCount || 0}}</span>
</template>
</el-table-column>
<el-table-column width="150" label="未激活数量" align="center" prop="unactivationCount">
<template #default="scope">
<span @click="todetails(scope.row,1)" class="viewspan">{{scope.row.unactivationCount || 0}}</span>
</template>
</el-table-column>
<el-table-column width="100" label="创建者" align="center" prop="createBy" />
<el-table-column width="180" label="创建时间" align="center" prop="createTime" />
<el-table-column width="100" label="更新者" align="center" prop="updateBy" />
<el-table-column width="180" label="更新时间" align="center" prop="updateTime" />
<!-- <el-table-column label="激活码" align="center" prop="activateCode" />
<el-table-column label="二维码" align="center" prop="qrCode">
<template #default="scope">
<div class="flexcenter">
<ImagePreview width="40px" height="40px" :src="scope.row.qrCode">
</ImagePreview>
</div>
</template>
</el-table-column> -->
<el-table-column label="操作" align="center" class-name="small-padding fixed-width">
<template #default="scope">
<el-button link type="primary" icon="Edit" @click="handleUpdate(scope.row)"
v-hasPermi="['mmxt:mmxtMeiyuTextbookActivateBatch:edit']">修改</el-button>
<el-button link type="primary" icon="Delete" @click="handleDelete(scope.row)"
v-hasPermi="['mmxt:mmxtMeiyuTextbookActivateBatch:remove']">删除</el-button>
</template>
</el-table-column>
</el-table>
<pagination v-show="total>0" :total="total" v-model:page="queryParams.pageNum"
v-model:limit="queryParams.pageSize" @pagination="getList" />
<!-- 添加或修改美美学堂智慧美育教材学习卡激活码对话框 -->
<el-dialog :title="title" v-model="open" width="500px" append-to-body>
<el-form ref="mmxtMeiyuTextbookActivateRef" :model="form" :rules="rules" label-width="80px">
<el-form-item label="所属教材" prop="textbookId">
<el-select-v2 class="input280" v-model="form.textbookId" :options="yshzTextbookList"
placeholder="请选择教材" filterable clearable @change="handleQuery" />
</el-form-item>
<el-form-item label="批次" prop="batchName">
<el-input class="input280" v-model="form.batchName" placeholder="请输入批次" />
</el-form-item>
<el-form-item label="地域名称" prop="regionId">
<el-tree-select class="input280" v-model="form.regionId" :data="yshzRegionOptions"
:props="{ value: 'regionId', label: 'regionName', children: 'children' }" value-key="id"
placeholder="请选择地域" check-strictly />
</el-form-item>
<el-form-item v-if="!form.batchId" label="生成数量" prop="generateCount">
<el-input class="input280" v-model="form.generateCount" placeholder="请输入生成数量" />
</el-form-item>
<div class="marginleft10">
<div v-if="form.createBy && form.createTime"><span
class="createds">创建信息</span>{{form.createBy}}{{form.createTime}}创建</div>
<div v-if="form.updateBy && form.updateTime"><span
class="createds">更新信息</span>{{form.updateBy}}{{form.updateTime}}更新</div>
</div>
</el-form>
<template #footer>
<div class="dialog-footer">
<el-button type="primary" @click="submitForm"> </el-button>
<el-button @click="cancel"> </el-button>
</div>
</template>
</el-dialog>
<detailsdaing ref="detailsdaingRef" />
</div>
</template>
<script setup name="MmxtMeiyuTextbookActivate">
import { onMounted } from "vue"
import { useRoute } from "vue-router"
import { selectTextbookEasy, selectMmxtMeiyuRegionByEasy, listMmxtMeiyuTextbookActivateBatch, getMmxtMeiyuTextbookActivateBatch, delMmxtMeiyuTextbookActivateBatch, addMmxtMeiyuTextbookActivateBatch, updateMmxtMeiyuTextbookActivateBatch } from "@/api/mmxt/mmxtMeiyuTextbookActivateBatch"
import { ElMessage, ElLoading } from 'element-plus'
import emitter from '@/utils/mitt';
import detailsdaing from "@/views/mmxt/mmxtMeiyuTextbookActivate/components/detailsdaing.vue"
const { proxy } = getCurrentInstance()
const yshzRegionOptions = ref([])
const yshzTextbookList = ref([])
const mmxtMeiyuTextbookActivateList = ref([])
const open = ref(false)
const loading = ref(true)
const showSearch = ref(true)
const ids = ref([])
const single = ref(true)
const multiple = ref(true)
const total = ref(0)
const title = ref("")
const route = useRoute()
const data = reactive({
form: {},
queryParams: {
pageNum: 1,
pageSize: 10,
textbookId: null,
batch: null,
regionId: null,
activateCode: null,
qrCode: null,
},
rules: {
textbookId: [
{ required: true, message: "教材不能为空", trigger: "blur" }
],
batch: [
{ required: true, message: "批次不能为空", trigger: "blur" }
],
regionId: [
{ required: true, message: "地域名称不能为空", trigger: "blur" }
],
generateCount: [
{ required: true, message: "生成数量不能为空", trigger: "blur" }
],
}
})
const { queryParams, form, rules } = toRefs(data)
/** 查询美美学堂智慧美育教材学习卡激活码列表 */
function getList() {
loading.value = true
listMmxtMeiyuTextbookActivateBatch(queryParams.value).then(response => {
mmxtMeiyuTextbookActivateList.value = response.rows
total.value = response.total
loading.value = false
})
}
//
function cancel() {
open.value = false
reset()
}
//
function reset() {
form.value = {
recordId: null,
textbookId: queryParams.value.textbookId,
subject: queryParams.value.subject,
batch: null,
regionId: null,
activateCode: null,
qrCode: null,
createTime: null,
createBy: null,
updateTime: null,
updateBy: null,
delFlag: null
}
proxy.resetForm("mmxtMeiyuTextbookActivateRef")
}
/** 搜索按钮操作 */
function handleQuery() {
queryParams.value.pageNum = 1
getList()
}
/** 重置按钮操作 */
function resetQuery() {
proxy.resetForm("queryRef")
handleQuery()
}
//
function handleSelectionChange(selection) {
ids.value = selection.map(item => item.batchId)
single.value = selection.length != 1
multiple.value = !selection.length
}
/** 新增按钮操作 */
function handleAdd() {
reset()
open.value = true
title.value = "添加教材学习卡激活码"
}
/** 修改按钮操作 */
function handleUpdate(row) {
reset()
const _recordId = row.batchId || ids.value
getMmxtMeiyuTextbookActivateBatch(_recordId).then(response => {
form.value = response.data
open.value = true
title.value = "修改教材学习卡激活码"
})
}
/** 提交按钮 */
function submitForm() {
proxy.$refs["mmxtMeiyuTextbookActivateRef"].validate(valid => {
if (valid) {
if (form.value.batchId != null) {
updateMmxtMeiyuTextbookActivateBatch(form.value).then(response => {
proxy.$modal.msgSuccess("修改成功")
open.value = false
getList()
})
} else {
const loading = ElLoading.service({ text: '正在生成激活码...', background: 'rgba(0, 0, 0, 0.7)' })
addMmxtMeiyuTextbookActivateBatch(form.value).then(response => {
loading.close()
proxy.$modal.msgSuccess("新增成功")
open.value = false
getList()
})
}
}
})
}
/** 删除按钮操作 */
function handleDelete(row) {
const _recordIds = row.batchId || ids.value
proxy.$modal.confirm('是否确认删除美美学堂智慧美育教材学习卡激活码编号为"' + _recordIds + '"的数据项?').then(function () {
return delMmxtMeiyuTextbookActivateBatch(_recordIds)
}).then(() => {
getList()
proxy.$modal.msgSuccess("删除成功")
}).catch(() => { })
}
/** 导出按钮操作 */
function handleExport() {
proxy.download('mmxt/mmxtMeiyuTextbookActivate/export', {
...queryParams.value
}, `mmxtMeiyuTextbookActivate_${new Date().getTime()}.xlsx`)
}
/**
* 核心行政区划懒加载函数
* @param node 当前点击的节点信息
* @param resolve 返回数据的回调函数
*/
function loadRegionNodes() {
// 1
selectMmxtMeiyuRegionByEasy().then(response => {
yshzRegionOptions.value = proxy.handleTree(response.data, "regionId")
})
}
function getlistYshztTextbook() {
selectTextbookEasy().then(response => {
yshzTextbookList.value = response.data.map(item => ({ label: item.textbookName, value: item.textbookId }))
})
}
const todetails = (row, type) => {
proxy.$refs.detailsdaingRef.opens(row.batchId, type)
}
onMounted(() => {
emitter.on('numberReflashlist', (msg) => {
getList();
});
if (route.query.textbookId) {
queryParams.value.textbookId = route.query.textbookId
from.value.textbookId = route.query.textbookId
}
if (route.query.subject) {
queryParams.value.subject = route.query.subject
}
})
getlistYshztTextbook()
loadRegionNodes()
getList()
</script>
<style lang="scss" scoped>
.viewspan {
color: #409EFF;
cursor: pointer;
}
.input150 {
width: 150px;
}
.input280 {
width: 280px;
}
</style>
Loading…
Cancel
Save