f120f0ea by lttnew

省级指派放开+级位考试优化+考点申请同步pc

1 parent f813fede
// dev
// const baseUrl_api = 'http://192.168.1.222:8787'
const baseUrl_api = 'http://192.168.1.222:8787'
// const baseUrl_api = 'http://47.98.186.233:8787'
const baseUrl_api = 'https://tk001.wxjylt.com/stage-api/'
// const baseUrl_api = 'https://tk001.wxjylt.com/stage-api/'
const loginImage_api = 'https://tk001.wxjylt.com/stage-api'
const payUrl = 'https://wxpay.cmbc.com.cn/mobilePlatform/appserver/lcbpPay.do'
......
<template>
<view class="add-apply-page">
<view v-if="activeSelectKey" class="level-dropdown-mask" @click="closeLevelDropdown"></view>
<!-- 顶部步骤条 -->
<view class="steps-bar">
<view :class="{ active: active >= 0, current: active == 0 }" class="step-item">
......@@ -101,8 +102,13 @@
</view>
<!-- 考生列表(红框主体) -->
<view class="student-list">
<view v-for="(n,index) in infoList" :key="index" class="student-card">
<view :class="{ 'dropdown-open': activeSelectKey }" class="student-list">
<view
v-for="(n,index) in infoList"
:key="n.id || n.perId || n.idcCode || index"
:class="{ 'select-open': activeSelectKey === getRowKey(n, index) }"
class="student-card"
>
<!-- 左侧:头像+考生信息 -->
<view class="card-left">
<view class="avatar">
......@@ -128,8 +134,27 @@
</view>
<view class="level-item">
<text class="level-label">考试级别</text>
<view class="select-wrapper exam-level-select" @click="changeLevelfather(n)">
<uni-data-select v-model="n.levelNew" :clear="false" :localdata="levelArr" @change="changeLevel"/>
<view class="select-wrapper exam-level-select">
<view class="exam-level-trigger" @click="toggleLevelDropdown(n, index)">
<text>{{ getLevelText(n.levelNew) || '请选择' }}</text>
<uni-icons color="#999" size="14" type="top"></uni-icons>
</view>
<view
v-if="activeSelectKey === getRowKey(n, index)"
class="level-dropdown-up"
>
<view class="level-dropdown-inner">
<view
v-for="item in getLevelOptions(n)"
:key="item.value"
:class="{ active: n.levelNew === item.value }"
class="level-dropdown-item"
@click.stop="chooseLevel(n, item)"
>
{{ item.text }}
</view>
</view>
</view>
</view>
</view>
<view class="level-item">
......@@ -218,6 +243,17 @@
</view>
</uni-popup>
<custom-modal
ref="confirmModalRef"
:title="confirmModal.title"
:content="confirmModal.content"
:cancel-text="confirmModal.cancelText"
:confirm-text="confirmModal.confirmText"
:show-cancel="confirmModal.showCancel"
@cancel="handleConfirmCancel"
@confirm="handleConfirmOk"
/>
</view>
</template>
......@@ -228,6 +264,7 @@ import {onLoad, onShow} from '@dcloudio/uni-app';
import config from '@/config.js'
import dayjs from 'dayjs'
import _ from 'underscore'
import customModal from '@/components/custom-modal.vue'
const app = getApp();
const memberInfo = app.globalData.memberInfo
......@@ -242,8 +279,19 @@ const active = ref(0)
const infoList = ref([])
const tablePersonInfo = ref({})
const transcript = ref([]) // 补全缺失变量
const activeSelectKey = ref('')
const confirmModalRef = ref(null)
const confirmModal = ref({
title: '提示',
content: '',
cancelText: '取消',
confirmText: '确定',
showCancel: true
})
let confirmOkAction = null
let confirmCancelAction = null
const levelArr = ref([{
const defaultLevelArr = [{
value: '10',
text: '十级'
}, {
......@@ -273,7 +321,8 @@ const levelArr = ref([{
}, {
value: '1',
text: '一级'
}])
}]
const levelArr = ref(defaultLevelArr.map(item => ({ ...item })))
const range = ref([{
value: '1',
......@@ -300,6 +349,103 @@ const idcTypeIndex = ref(0)
let examId
function openConfirmModal(options = {}) {
confirmModal.value = {
title: options.title || '提示',
content: options.content || '',
cancelText: options.cancelText || '取消',
confirmText: options.confirmText || '确定',
showCancel: options.showCancel !== false
}
confirmOkAction = typeof options.onConfirm === 'function' ? options.onConfirm : null
confirmCancelAction = typeof options.onCancel === 'function' ? options.onCancel : null
confirmModalRef.value?.open()
}
function handleConfirmOk() {
const action = confirmOkAction
confirmOkAction = null
confirmCancelAction = null
if (action) action()
}
function handleConfirmCancel() {
const action = confirmCancelAction
confirmOkAction = null
confirmCancelAction = null
if (action) action()
}
function getRowKey(row, index = 0) {
return String(row.id || row.perId || row.personId || row.idcCode || index)
}
function cloneLevelOptions(list = defaultLevelArr) {
return list.map(item => ({ ...item }))
}
function normalizeLevelOptions(list) {
if (!Array.isArray(list) || list.length === 0) {
return cloneLevelOptions()
}
const remoteList = list.map(item => ({
...item,
value: String(item.value ?? item.level ?? item.id ?? '')
}))
return defaultLevelArr.map(defaultItem => {
const remoteItem = _.find(remoteList, item => {
return item.value === String(defaultItem.value) || item.name === defaultItem.text || item.text === defaultItem.text
})
const source = remoteItem || defaultItem
const disabled = source.status === undefined ? (source.disabled || source.disable || false) : !source.status
return {
...source,
value: String(defaultItem.value),
text: source.text || source.name || defaultItem.text,
disabled,
disable: disabled
}
})
}
function getLevelOptions(row) {
if (!row.levelOptions || row.levelOptions.length === 0) {
row.levelOptions = cloneLevelOptions()
}
return row.levelOptions
}
function getLevelText(value) {
if (!value) return ''
const allOptions = [...defaultLevelArr, ...levelArr.value]
const option = _.find(allOptions, item => String(item.value) === String(value))
return option?.text || `${szToHz(value)}级`
}
function setDefaultLevel(row) {
row.levelOld = row.levelOld ? String(row.levelOld) : ''
row.levelNew = row.levelNew ? String(row.levelNew) : ''
if (row.levelOld) {
row.levelRecommend = String(parseInt(row.levelOld) - 1)
if (row.levelRecommend === '0') {
row.levelRecommend = '1'
}
} else {
row.levelRecommend = '9'
}
// 原级别是一级时不能默认推荐,其他情况按推荐级别回填,保证二次添加后列表能显示考试级别。
if (row.levelOld === '1') {
row.levelNew = ''
} else if (!row.levelNew) {
row.levelNew = row.levelRecommend
}
if (!row.isPass) {
row.isPass = '1'
}
}
onLoad(option => {
if (app.globalData.isLogin) {
initData(option)
......@@ -586,25 +732,8 @@ function getChosedStudentList() {
}
api.getStudentList(obj).then(res => {
_.each(res.rows, (d) => {
if (d.levelOld) {
d.levelRecommend = (parseInt(d.levelOld) - 1) + ''
if (d.levelRecommend === '0') {
d.levelRecommend = '1'
}
} else {
d.levelRecommend = '9'
}
// 原级别是一级时,levelNew 默认为空,不使用推荐值
if (d.levelOld === '1') {
d.levelNew = ''
} else if (!d.levelNew) {
d.levelNew = d.levelRecommend
}
if (!d.isPass) {
d.isPass = '1'
}
setDefaultLevel(d)
d.levelOptions = cloneLevelOptions()
if (d.photo && d.photo.indexOf('http') == -1) {
d.photo = config.baseUrl_api + d.photo
}
......@@ -646,7 +775,25 @@ function szToHz(num) {
let nowRow
function changeLevelfather(row, flag = 0) {
function toggleLevelDropdown(row, index = 0) {
const rowKey = getRowKey(row, index)
if (activeSelectKey.value === rowKey) {
closeLevelDropdown()
return
}
nowRow = row
activeSelectKey.value = rowKey
getLevelOptions(row)
changeLevelfather(row, index)
}
function closeLevelDropdown() {
activeSelectKey.value = ''
}
function changeLevelfather(row, index = 0, flag = 0) {
nowRow = row
activeSelectKey.value = getRowKey(row, index)
const data = _.map(infoList.value, (d) => {
return {
id: d.id,
......@@ -662,21 +809,25 @@ function changeLevelfather(row, flag = 0) {
// perId: row.perId,
status: flag
}).then(res => {
levelArr.value = res.data
for (let l of levelArr.value) {
l.text = l.name
l.disabled = !(l.status)
}
const options = normalizeLevelOptions(res.data)
row.levelOptions = options
levelArr.value = options
})
}
function changeLevel(e) {
// 切换考试级别时弹出确认框
uni.showModal({
function chooseLevel(row, item) {
if (!row) return
const oldLevel = row.levelNew
row.levelNew = String(item.value)
changeLevel(row, oldLevel)
}
function changeLevel(row, oldLevel) {
nowRow = row || nowRow
openConfirmModal({
title: '提示',
content: '请仔细核实本次等级申报是否正确!',
success: function (res) {
if (res.confirm) {
onConfirm: function () {
// 保存当前行数据
const data = _.map(infoList.value, (d) => {
return {
......@@ -691,16 +842,16 @@ function changeLevel(e) {
transcript: form.value.transcript,
status: 0
}).then(() => {
closeLevelDropdown()
// 保存成功后更新统计
getTablePersonInfo()
})
} else {
// 取消时恢复为推荐级别
nowRow.levelNew = nowRow.levelRecommend != 0 ? nowRow.levelRecommend : ''
}
},
fail: function (res) {
nowRow.levelNew = nowRow.levelRecommend != 0 ? nowRow.levelRecommend : ''
onCancel: function () {
if (nowRow) {
nowRow.levelNew = oldLevel !== undefined ? oldLevel : (nowRow.levelRecommend != 0 ? nowRow.levelRecommend : '')
}
closeLevelDropdown()
}
})
}
......@@ -719,11 +870,10 @@ function submitForm2(flag) {
return
}
uni.showModal({
openConfirmModal({
title: '提示',
content: `请确认人员照片是否已更新?`,
success: function (res) {
if (res.confirm) {
onConfirm: function () {
// saveStep2(flag).then(() => {
// uni.navigateTo({
// url: `/level/paymentDetail?examId=${form.value.examId}`
......@@ -733,7 +883,6 @@ function submitForm2(flag) {
url: `/level/paymentDetail?examId=${form.value.examId}`
})
}
}
})
} else {
saveStep2(flag).then(() => {
......@@ -759,17 +908,15 @@ function saveStep2(flag) {
}
function handleDelete(row) {
uni.showModal({
openConfirmModal({
title: '提示',
content: `确定删除${row.realName}?`,
success: function (res) {
if (res.confirm) {
onConfirm: function () {
api.dellevelPerson(row.id).then(() => {
uni.showToast({title: '操作成功', icon: 'none'})
getChosedStudentList()
})
}
}
})
}
</script>
......@@ -780,6 +927,16 @@ function handleDelete(row) {
padding-bottom: 120rpx;
}
.level-dropdown-mask {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
z-index: 90;
background: transparent;
}
/* 顶部步骤条 */
.steps-bar {
display: flex;
......@@ -986,9 +1143,14 @@ function handleDelete(row) {
position: relative;
z-index: 1;
&.dropdown-open {
z-index: 110;
}
.student-card {
position: relative;
z-index: 1;
overflow: visible;
// display: flex;
// align-items: center;
......@@ -999,6 +1161,10 @@ function handleDelete(row) {
margin-bottom: 20rpx;
box-shadow: 0 4rpx 16rpx rgba(0, 0, 0, 0.04);
&.select-open {
z-index: 120;
}
/* 左侧:头像+考生信息 */
.card-left {
display: flex;
......@@ -1084,7 +1250,64 @@ function handleDelete(row) {
.select-wrapper {
width: 160rpx;
position: relative;
z-index: 1;
z-index: 2;
overflow: visible;
}
.exam-level-select {
z-index: 130;
.exam-level-trigger {
display: flex;
align-items: center;
justify-content: space-between;
height: 70rpx;
padding: 0 20rpx;
box-sizing: border-box;
border: 1rpx solid #e5e5e5;
border-radius: 8rpx;
background: #fff;
font-size: 28rpx;
color: #333;
}
.level-dropdown-up {
position: absolute;
left: 0;
bottom: 78rpx;
width: 180rpx;
background: #fff;
border-radius: 12rpx;
box-shadow: 0 8rpx 28rpx rgba(0, 0, 0, 0.14);
z-index: 180;
padding: 8rpx 0;
box-sizing: border-box;
}
.level-dropdown-inner {
height: auto;
}
.level-dropdown-item {
height: 68rpx;
line-height: 68rpx;
padding: 0 24rpx;
font-size: 28rpx;
color: #333;
text-align: left;
&.active {
color: #AD181F;
font-weight: 600;
background: #FFF5F5;
}
&.disabled {
color: #c8c9cc;
background: #fafafa;
}
}
}
}
}
......@@ -1278,4 +1501,5 @@ function handleDelete(row) {
font-size: 28rpx;
margin-top: 16rpx;
}
</style>
......
<template>
<view>
<view class="apply-detail-page">
<view class="wBox">
<view class="tt">考级基本信息</view>
<view class="ddd">
......@@ -228,6 +228,12 @@
</script>
<style scoped lang="scss">
.apply-detail-page {
min-height: 100vh;
padding-bottom: calc(60rpx + env(safe-area-inset-bottom));
box-sizing: border-box;
}
.wBox {
width: 700rpx;
padding: 30rpx;
......
......@@ -12,7 +12,7 @@
<radio :checked="form.selfSelect == '1'" class="custom-radio" value="1"/>
<text class="radio-text">自行录入考官(级位考官)</text>
</label>
<label v-if="shenForm.memberEpAudit==1" class="radio-item">
<label class="radio-item">
<radio :checked="form.selfSelect == '0'" class="custom-radio" value="0"/>
<text class="radio-text">省跆协指派考官</text>
</label>
......
......@@ -405,10 +405,11 @@ function checkDialogs() {
async function checkExamPointDialog() {
console.log('checkExamPointDialog', app.globalData.userInfo.hintFlag )
const [err, res] = await to(api.getMyRecentExam())
if (err || !res?.data) return
const status = res.data?.auditStatus
if ((status == 0 || status == 3) &&
// const [err, res] = await to(api.getMyRecentExam())
// if (err || !res?.data) return
// const status = res.data?.auditStatus
// (status == 0 || status == 3) &&
if (
app.globalData.memberInfo?.activeStatus == 1 &&
app.globalData.authenticationStatus == 2 &&
app.globalData.deptType == 6 &&
......
Styling with Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!