1fa3debe by lttnew

审核

1 parent 9b888601
......@@ -913,7 +913,7 @@ export function getVerityMergeList(params) {
}
// 中跆协审核列表
export function auditList(params) {
export function examauditList(params) {
return request({
url: '/exam/info/list',
method: 'get',
......@@ -923,8 +923,16 @@ export function auditList(params) {
// 中跆协审核提交
export function auditJi(data) {
// 基础 URL
let url = `/exam/info/auditJi/${data.ids}?flag=${data.flag}&ids=${data.ids}`;
// reason 有值才拼接
if (data.reason && data.reason.trim() !== '') {
url += `&reason=${data.reason}`;
}
return request({
url: `/exam/info/auditJi/${data.ids}?flag=${data.flag}&reason=${data.reason}&ids=${data.ids}`,
url: url,
method: 'post',
params: data
})
......
// dev
const baseUrl_api = 'http://192.168.1.137:8787'
// const baseUrl_api = 'http://tk001.wxjylt.com/stage-api'
// const baseUrl_api = 'http://192.168.1.137:8787'
const baseUrl_api = 'http://tk001.wxjylt.com/stage-api'
const loginImage_api = 'http://tk001.wxjylt.com/stage-api'
const payUrl = 'https://wxpay.cmbc.com.cn/mobilePlatform/appserver/lcbpPay.do'
......
......@@ -77,7 +77,8 @@
<view class="content">
<view class="status">
<text v-if="n.auditResult==1" class="text-success">审核通过</text>
<text v-if="n.auditResult!=1" class="text-danger"> 审核拒绝</text>
<text v-else-if="n.auditResult==0" class="text-danger">审核拒绝</text>
<text v-else class="text-primary">审核中</text>
</view>
<view class="name">{{ n.auditDeptName }}</view>
<!-- <view class="name">{{ index + 1 }}</view>-->
......
......@@ -6,11 +6,14 @@
<view class="time">{{n.handleDate||'待审批'}}</view>
<view class="content">
<view class="status">
<text v-if="n.auditStatus==0" class="text-primary">审核中</text>
<text v-if="n.auditResult==1" class="text-success">审核通过</text>
<text v-else-if="n.auditResult==0" class="text-danger">审核拒绝</text>
<text v-else class="text-primary">审核中</text>
<!-- <text v-if="n.auditStatus==0" class="text-primary">审核中</text>
<text v-if="n.auditStatus==1" class="text-success">审核通过</text>
<text v-if="n.auditStatus==2" class="text-danger">审核拒绝</text>
<text v-if="n.auditStatus==3" class="text-warning">已撤回</text>
<text v-if="n.auditStatus==100" class="text-primary">审核中</text>
<text v-if="n.auditStatus==100" class="text-primary">审核中</text> -->
</view>
<!-- <view class="name">{{index+1}}</view> -->
<view class="deptName">{{n.handlerDeptName}}</view>
......
......@@ -52,9 +52,8 @@
<view class="content">
<view class="status">
<text v-if="n.auditResult==1" class="text-success">审核通过</text>
<text v-if="n.auditResult==2" class="text-danger"> 审核拒绝</text>
<text v-if="n.auditResult==0" class="text-primary"> 审核中</text>
<text v-if="n.auditResult==3" class="text-warning">已撤回</text>
<text v-else-if="n.auditResult==0" class="text-danger">审核拒绝</text>
<text v-else class="text-primary">审核中</text>
</view>
<!-- <view class="name">{{index+1}}</view> -->
......
......@@ -100,7 +100,7 @@
uni.showLoading({ title: '加载中', mask: true })
totalCost.value = 0
totalNum.value = 0
api.auditList(queryParams.value).then(response => {
api.examauditList(queryParams.value).then(response => {
uni.hideLoading()
infoList.value = response.rows || []
total.value = response.total || 0
......
......@@ -102,7 +102,9 @@ function doSubmit() {
flag: form.value.flag,
reason: form.value.reason || ''
}
if(!form.value.reason ){
delete params.reason
}
api.auditJi(params).then(res => {
uni.showToast({
title: '操作成功',
......
......@@ -76,6 +76,20 @@
}
}, {
"path": "pages/rank/scoreDetail",
"style": {
"navigationBarTitleText": "成绩详情",
"enablePullDownRefresh": false
}
}, {
"path": "pages/rank/scoreAudit",
"style": {
"navigationBarTitleText": "成绩审核",
"enablePullDownRefresh": false
}
}, {
"path": "pages/rank/cert",
"style": {
"navigationBarTitleText": "证书发布",
......
......@@ -254,7 +254,7 @@
<image :src="config.baseUrl_api+'/fs/static/icon/19.png'"/>
考试审核
</view>
<view @click="goPath('/pages/rank/scoreApproval?type=2')">
<view @click="goPath('/pages/rank/scoreApproval?type=3')">
<uni-badge :text="numData.duanCjCount" class="potag"/>
<image :src="config.baseUrl_api+'/fs/static/icon/19.png'"/>
成绩审核
......@@ -263,7 +263,7 @@
<image :src="config.baseUrl_api+'/fs/static/icon/20.png'"/>
证书发布
</view>
<view @click="goPath('/personalVip/order?type=3')">
<view @click="goPath('/personalVip/order?type=4')">
<image :src="config.baseUrl_api+'/fs/static/icon/6.png'"/>
订单列表
</view>
......@@ -271,12 +271,12 @@
<view class="ttt">越段考试</view>
<view class="girdBox">
<view @click="goPath('/pages/rank/approval?type=3')">
<view @click="goPath('/pages/rank/approval?type=4')">
<uni-badge :text="numData.yueduanCount" class="potag"/>
<image :src="config.baseUrl_api+'/fs/static/icon/21.png'"/>
考试审核
</view>
<view @click="goPath('/pages/rank/scoreApproval?type=3')">
<view @click="goPath('/pages/rank/scoreApproval?type=5')">
<uni-badge :text="numData.yueduanCjCount" class="potag"/>
<image :src="config.baseUrl_api+'/fs/static/icon/22.png'"/>
成绩审核
......
......@@ -132,9 +132,9 @@
<view class="content">
<view class="status">
<text v-if="n.auditResult==1" class="text-success">审核通过</text>
<text v-if="n.auditResult==2" class="text-danger">审核拒绝</text>
<text v-if="n.auditResult==0" class="text-primary">审核中</text>
<text v-if="n.auditResult==3" class="text-warning">已撤回</text>
<text v-else-if="n.auditResult==0" class="text-danger">审核拒绝</text>
<text v-else class="text-primary">审核中</text>
</view>
<view class="deptName">{{ n.auditDeptName || n.deptName || '--' }}</view>
<view v-if="n.auditMsg">备注:{{ n.auditMsg }}</view>
......
......@@ -7,12 +7,12 @@
<view class="appList">
<view class="appItem" v-for="item in infoList" :key="item.recordId" >
<view @click="goDetail(item)">
<view class="status" >
<view class="status" v-if="item.statusStr">
<text :class="{
'text-primary-bg':item.auditStatus=='0',
'text-success-bg':item.auditStatus=='1',
'text-danger-bg':item.auditStatus=='2',
'text-warning-bg':item.auditStatus=='3'
'text-primary-bg':item.auditStatus=='1',
'text-success-bg':item.status=='2',
'text-danger-bg':item.status=='3',
'text-warning-bg':item.status=='4'
}">{{ item.statusStr }}</text>
</view>
......@@ -33,9 +33,8 @@
<view class="pp esp">考段日期:{{item.startTime.substring(0,16)}}{{item.endTime.substring(0,16)}}</view>
</view>
<view class="func" v-if="item.auditStatus=='0'">
<button @click="audit(item,'2')">拒绝</button>
<button @click="audit(item,'1')">同意</button>
<view class="func" >
<button @click="goApproval(item)" v-if="item.status=='1'">审核</button>
</view>
<view class="func" v-if="item.isView=='1' && item.status=='1' && item.rankStatus =='0'">
<button @click="handleBack(item)">撤回</button>
......@@ -50,171 +49,96 @@
</template>
<script setup>
import * as examApi from '@/common/api_exam.js'
import config from '@/config.js'
import _ from 'underscore'
import { ref } from 'vue'
import { onLoad,onShow } from '@dcloudio/uni-app'
const app = getApp();
const queryParams = ref({
status: '0',
rankStatus:'0'
})
const current = ref()
const navs = ref(['审核中', '审核通过', '审核拒绝'])
const statusArr = ['审批中', '审批通过', '审批拒绝', '审批撤回']
const deptType = ref('')
const infoList = ref([])
const total = ref(0)
onLoad((options)=>{
queryParams.value.type=options.type
})
onShow(() => {
if (app.globalData.isLogin) {
init()
} else {
app.firstLoadCallback = () => {
init()
};
}
})
function init(){
deptType.value = app.globalData.deptType
getList()
}
function onClickItem(e) {
queryParams.value.status = e.currentIndex
getList()
}
function getList() {
uni.showLoading({
title: '加载中',
mask: true
})
examApi.getVerityList(queryParams.value).then(res => {
uni.hideLoading()
const list = []
_.each(res.rows, r => {
const item = JSON.parse(r.content)
item.recordId = r.recordId
item.auditStatus = r.auditStatus
item.submitStatus = r.submitStatus
item.distributeTime = r.distributeTime
item.statusStr = statusArr[r.auditStatus]
item.sourceData = r
item.scoreStatus = r.scoreStatus
item.status = r.status
item.isView = r.isView
item.payStatus = r.payStatus
item.rankStatus = r.rankStatus
item.processCentBar = r.processCentBar
list.push(item)
import * as api from '@/common/api.js'
import config from '@/config.js'
import { ref } from 'vue'
import { onLoad, onShow } from '@dcloudio/uni-app'
const app = getApp()
const statusValues = ['', '1', '2', '3']
const navs = ref(['全部', '审批中', '审批通过', '审批拒绝'])
const current = ref(0)
const queryParams = ref({
auditSelectType: '2',
rankStatus: '0',
// status: '',
pageNum: 1,
pageSize: 10
})
infoList.value = list
total.value = res.total
})
}
function audit(item, flag) {
console.log(item.sourceData)
var obj = {
flag: flag,
reason: null,
id: item.recordId
const infoList = ref([])
const total = ref(0)
const totalCost = ref(0)
const totalNum = ref(0)
onLoad((options) => {
queryParams.value.type = options.type
queryParams.value.auditSelectType = options.type
if (options.type == '2') {
uni.setNavigationBarTitle({ title: '段位考试审核' })
} else if (options.type == '4') {
uni.setNavigationBarTitle({ title: '越段考试审核' })
}
if (flag == '2') {
// 拒绝
// 弹出框填写理由
uni.showModal({
title: '请输入拒绝理由',
editable: true,
success: function(res) {
if (res.confirm) {
if (!res.content) {
uni.showToast({
title: '请输入拒绝理由',
icon: 'none'
})
onShow(() => {
if (app.globalData.isLogin) {
getList()
} else {
obj.reason = res.content
doApproval(obj)
}
}
}
})
} else if (flag == '1') {
// 二次确认
uni.showModal({
title: '提示',
content: `确定审批通过吗`,
success: function(res) {
if (res.confirm) {
doApproval(obj)
}
app.firstLoadCallback = () => { getList() }
}
})
function onClickItem(e) {
current.value = e.currentIndex
queryParams.value.status = statusValues[e.currentIndex]
getList()
}
}
function doApproval(obj) {
uni.showLoading({
title: '加载中'
})
examApi.doMergeFlows(obj).then((res) => {
function getList() {
uni.showLoading({ title: '加载中', mask: true })
totalCost.value = 0
totalNum.value = 0
api.examauditList(queryParams.value).then(res => {
uni.hideLoading()
uni.showToast({
title: '操作成功',
icon: 'none'
infoList.value = res.rows || []
total.value = res.total || 0
infoList.value.forEach(item => {
totalCost.value += Number(item.price) || 0
totalNum.value += Number(item.totalNum) || 0
})
getList()
}).catch(() => {
uni.hideLoading()
})
}
}
function goDetail(item) {
let path = `/pages/rank/applyDetail?examId=${item.examId}`
function goDetail(item) {
uni.navigateTo({
url: path
});
}
function handleBack(row){
uni.showModal({
title: '请输入撤回理由',
editable: true,
success: function(res) {
if (res.confirm) {
if (!res.content) {
uni.showToast({
title: '请输入撤回理由',
icon: 'none'
url: `/pages/rank/applyDetail?examId=${item.examId}&type=1`
})
} else {
var obj = {
flag: '2',
reason: res.content,
recordId: row.recordId
}
api.doVerityBack(obj).then(rr=>{
uni.showToast({
title: '操作成功',
icon: 'none'
})
getList()
})
}
}
}
function goApproval(item) {
uni.navigateTo({
url: `/level/ztx/memberAuditPage?ids=${item.examId}`
})
}
</script>
<style lang="scss" scoped>
.stat-row {
display: flex;
gap: 40rpx;
padding: 20rpx 30rpx;
background: #fff;
font-size: 26rpx;
color: #666;
.red {
color: #C4121B;
font-weight: 600;
}
}
</style>
......
......@@ -3,51 +3,50 @@
<uni-segmented-control class="whitebg" :current="current" :values="navs" @clickItem="onClickItem"
styleType="text" activeColor="#AD181F"></uni-segmented-control>
<!-- 段位考试审核 -->
<!-- <view v-show="infoList.length>0" class="stat-row">
<view class="stat-item">费用合计:<text class="red">{{ totalCost.toFixed(2) }}</text></view>
<view class="stat-item">考试人数:<text class="red">{{ totalNum }}</text></view>
</view> -->
<view class="appList">
<view class="appItem" v-for="item in infoList" :key="item.recordId">
<view class="appItem" v-for="item in infoList" :key="item.examId">
<view @click="goDetail(item)">
<view class="status">
<text :class="{
'text-primary-bg':item.auditStatus=='0',
'text-success-bg':item.auditStatus=='1',
'text-danger-bg':item.auditStatus=='2',
'text-warning-bg':item.auditStatus=='3'
}">{{ item.statusStr }}</text>
'text-primary-bg': item.scoreStatus=='0',
'text-success-bg': item.scoreStatus=='2',
'text-danger-bg': item.scoreStatus=='3',
'text-warning-bg': item.scoreStatus=='4'
}">{{ item.scoreStatusStr }}</text>
</view>
<view class="date" v-if="item.status!='0'&&item.submitTime">
<uni-icons type="calendar-filled" size="16" color="#AD181F"></uni-icons>
提交时间:{{item.submitTime}}
提交时间:{{ item.submitTime }}
</view>
<view class="text-primary">{{item.examCode}}</view>
<view class="name mt10"><text class="dot"></text>{{item.name}}</view>
<view class="text-primary">{{ item.examCode }}</view>
<view class="name mt10">{{ item.name }}</view>
<view class="flexbox">
<view>
申请日期
<view>{{item.applyTime.substring(0, 10)}}</view>
<view>{{ item.applyTime ? item.applyTime.substring(0, 10) : '--' }}</view>
</view>
<view>
考段考生数
<view>{{item.totalNum}}</view>
<view>{{ item.totalNum }}</view>
</view>
<view>
总金额
<view>
<text class="text-danger">¥{{(item.totalAmount*1).toFixed(2)}}</text>
</view>
<view><text class="text-danger">¥{{ (Number(item.totalAmount) || 0).toFixed(2) }}</text></view>
</view>
</view>
<view class="pp esp">考段日期:{{item.startTime.substring(0,16)}}{{item.endTime.substring(0,16)}}
<view class="pp esp">考段日期:{{ item.startTime ? item.startTime.substring(0, 16) : '--' }}{{ item.endTime ? item.endTime.substring(0, 16) : '--' }}</view>
</view>
</view>
<view class="func" v-if="item.auditStatus=='0'">
<button @click="audit(item,'2')">拒绝</button>
<button @click="audit(item,'1')">同意</button>
<view class="func" v-if="item.scoreStatus=='1'">
<button @click="goApproval(item)">审核</button>
</view>
</view>
</view>
<view class="nodata" v-if="infoList.length==0">
<image mode="aspectFit" :src="config.baseUrl_api + '/fs/static/nodata.png'"></image>
<text>暂无数据</text>
......@@ -56,159 +55,96 @@
</template>
<script setup>
import * as examApi from '@/common/api_exam.js'
import _ from 'underscore'
import {
ref
} from 'vue'
import {
onLoad,
onShow
} from '@dcloudio/uni-app'
import config from '@/config.js'
const app = getApp();
import * as api from '@/common/api.js'
import config from '@/config.js'
import { ref } from 'vue'
import { onLoad, onShow } from '@dcloudio/uni-app'
const app = getApp()
const statusValues = ['', '1', '2', '3']
const navs = ref(['全部', '审核中', '审核通过', '审核拒绝'])
const current = ref(0)
const statusArr = ['审批中', '审批通过', '审批拒绝', '审批撤回']
const queryParams = ref({
status: '0',
rankStatus: '1'
status: '',
pageNum: 1,
pageSize: 50
})
const current = ref()
const navs = ref(['审核中', '审核通过', '审核拒绝'])
const statusArr = ['审批中', '审批通过', '审批拒绝', '审批撤回']
const deptType = ref('')
const infoList = ref([])
const total = ref(0)
const totalCost = ref(0)
const totalNum = ref(0)
onLoad((options) => {
queryParams.value.type = options.type
if (options.type == 2) {
uni.setNavigationBarTitle({
title: '段位考试审核'
})
}
if (options.type == 3) {
uni.setNavigationBarTitle({
title: '越段考试审核'
})
queryParams.value.auditSelectType = options.type
if (options.type == '3') {
uni.setNavigationBarTitle({ title: '段位成绩审核' })
} else if (options.type == '5') {
uni.setNavigationBarTitle({ title: '越段成绩审核' })
}
})
onShow(() => {
if (app.globalData.isLogin) {
init()
getList()
} else {
app.firstLoadCallback = () => {
init()
};
app.firstLoadCallback = () => { getList() }
}
})
function init() {
uni.showLoading({
title: '加载中'
})
deptType.value = app.globalData.deptType
getList()
}
function onClickItem(e) {
uni.showLoading({
title: '加载中'
})
queryParams.value.status = e.currentIndex
current.value = e.currentIndex
queryParams.value.scoreStatus = statusValues[e.currentIndex]
getList()
}
function getList() {
examApi.getVerityList(queryParams.value).then(res => {
uni.showLoading({ title: '加载中', mask: true })
totalCost.value = 0
totalNum.value = 0
api.examauditList(queryParams.value).then(res => {
uni.hideLoading()
const list = []
_.each(res.rows, r => {
const item = JSON.parse(r.content)
item.recordId = r.recordId
item.auditStatus = r.auditStatus
item.submitStatus = r.submitStatus
item.distributeTime = r.distributeTime
item.statusStr = statusArr[r.auditStatus]
item.sourceData = r
item.scoreStatus = r.scoreStatus
item.status = r.status
item.isView = r.isView
item.payStatus = r.payStatus
item.rankStatus = r.rankStatus
item.processCentBar = r.processCentBar
list.push(item)
})
infoList.value = list
total.value = res.total
infoList.value = res.rows || []
total.value = res.total || 0
infoList.value.forEach(item => {
item.statusStr = statusArr[item.auditStatus] || '审批中'
totalCost.value += Number(item.totalAmount) || 0
totalNum.value += Number(item.totalNum) || 0
})
}
function audit(item, flag) {
console.log(item.sourceData)
var obj = {
flag: flag,
reason: null,
id: item.recordId
}
if (flag == '2') {
// 拒绝
// 弹出框填写理由
uni.showModal({
title: '请输入拒绝理由',
editable: true,
success: function(res) {
if (res.confirm) {
if (!res.content) {
uni.showToast({
title: '请输入拒绝理由',
icon: 'none'
})
} else {
obj.reason = res.content
doApproval(obj)
}
}
}
})
} else if (flag == '1') {
// 二次确认
uni.showModal({
title: '提示',
content: `确定审批通过吗`,
success: function(res) {
if (res.confirm) {
doApproval(obj)
}
}
}).catch(() => {
uni.hideLoading()
})
}
}
function doApproval(obj) {
uni.showLoading({
title: '加载中',
mask: true
})
examApi.doMergeFlows(obj).then((res) => {
uni.hideLoading()
uni.showToast({
title: '操作成功',
icon: 'none'
})
getList()
function goApproval(item) {
uni.navigateTo({
url: `/pages/rank/scoreAudit?ids=${item.examId}`
})
}
function goDetail(item) {
let path = `/pages/rank/applyDetail?examId=${item.examId}`
uni.navigateTo({
url: path
});
url: `/pages/rank/scoreDetail?examId=${item.examId}&type=${queryParams.value.type}`
})
}
</script>
<style lang="scss" scoped>
.stat-row {
display: flex;
gap: 40rpx;
padding: 20rpx 30rpx;
background: #fff;
font-size: 26rpx;
color: #666;
.red {
color: #C4121B;
font-weight: 600;
}
}
</style>
......
<template>
<view class="audit-page">
<view class="form-section">
<view class="section-header">
<uni-icons type="edit" size="18" color="#AD181F"></uni-icons>
<text class="section-title">审核信息</text>
</view>
<view class="form-card">
<view class="form-item">
<text class="form-label">审批结果</text>
<radio-group @change="onFlagChange">
<view class="radio-group">
<label class="radio-item" :class="{ selected: form.flag == '1' }">
<radio value="1" :checked="form.flag == '1'" color="#C4121B" />
<text>审批通过</text>
</label>
<label class="radio-item" :class="{ selected: form.flag == '0' }">
<radio value="0" :checked="form.flag == '0'" color="#C4121B" />
<text>审批拒绝</text>
</label>
</view>
</radio-group>
</view>
<view class="form-item">
<text class="form-label">备注</text>
<textarea
v-model="form.reason"
class="textarea"
placeholder="请输入备注信息(拒绝时必填)"
:maxlength="500"
/>
</view>
</view>
</view>
<view class="submit-wrap">
<button class="btn-cancel" @click="goBack">取消</button>
<button class="btn-submit" @click="doSubmit" :disabled="submitting">
<text v-if="!submitting">确认提交</text>
<text v-else>提交中...</text>
</button>
</view>
</view>
</template>
<script setup>
import * as api from '@/common/api.js'
import { ref } from 'vue'
import { onLoad } from '@dcloudio/uni-app'
const ids = ref('')
const submitting = ref(false)
const form = ref({
flag: '1',
reason: ''
})
onLoad((options) => {
if (options.ids) ids.value = options.ids
})
function goBack() {
uni.navigateBack()
}
function onFlagChange(e) {
form.value.flag = e.detail.value
}
function doSubmit() {
if (form.value.flag == '0' && !form.value.reason) {
uni.showToast({ title: '请输入拒绝理由', icon: 'none' })
return
}
if (submitting.value) return
submitting.value = true
const params = {
ids: ids.value,
flag: form.value.flag,
reason: form.value.reason || ''
}
if(!form.value.reason ){
delete params.reason
}
api.auditJi(params).then(res => {
uni.showToast({ title: '操作成功', icon: 'success' })
setTimeout(() => { uni.navigateBack() }, 1500)
}).catch(err => {
console.error('审核失败', err)
uni.showToast({ title: '操作失败', icon: 'none' })
submitting.value = false
})
}
</script>
<style lang="scss" scoped>
.audit-page {
min-height: 100vh;
background-color: #f5f5f5;
padding: 20rpx;
box-sizing: border-box;
}
.form-section {
background-color: #fff;
border-radius: 16rpx;
padding: 30rpx;
margin-bottom: 20rpx;
}
.section-header {
display: flex;
align-items: center;
margin-bottom: 30rpx;
.section-title {
font-size: 30rpx;
font-weight: 600;
color: #333;
margin-left: 10rpx;
}
}
.form-card {
.form-item {
margin-bottom: 30rpx;
&:last-child {
margin-bottom: 0;
}
.form-label {
display: block;
font-size: 28rpx;
color: #333;
margin-bottom: 16rpx;
font-weight: 500;
}
.radio-group {
display: flex;
gap: 24rpx;
}
.radio-item {
flex: 1;
display: flex;
align-items: center;
justify-content: center;
gap: 12rpx;
font-size: 28rpx;
color: #666;
padding: 20rpx 0;
border-radius: 12rpx;
border: 2rpx solid #eee;
background: #fafafa;
&.selected {
color: #C4121B;
border-color: #C4121B;
background: #fff5f5;
font-weight: 500;
}
radio {
transform: scale(0.8);
}
}
.textarea {
width: 100%;
height: 200rpx;
border: 1rpx solid #eee;
border-radius: 12rpx;
padding: 20rpx;
font-size: 28rpx;
color: #333;
background-color: #fafafa;
box-sizing: border-box;
}
}
}
.submit-wrap {
position: fixed;
bottom: 0;
left: 0;
right: 0;
height: 110rpx;
background-color: #fff;
display: flex;
align-items: center;
justify-content: center;
gap: 30rpx;
padding: 0 30rpx;
box-shadow: 0 -4rpx 20rpx rgba(0, 0, 0, 0.05);
button {
flex: 1;
height: 80rpx;
line-height: 80rpx;
font-size: 28rpx;
border-radius: 40rpx;
border: none;
}
.btn-cancel {
background-color: #f5f5f5;
color: #666;
}
.btn-submit {
background: #C4121B;
color: #fff;
&[disabled] {
background: #ccc;
}
}
}
</style>
<template>
<view>
<scroll-view scroll-y class="detail-content">
<!-- 基本信息 -->
<view class="card">
<view class="card-header">
<view class="header-left">考试信息</view>
</view>
<view class="card-body">
<view class="info-row">
<text class="label">考试名称</text>
<text class="value">{{ form.name || '--' }}</text>
</view>
<view class="info-row">
<text class="label">考试日期</text>
<text class="value">{{ form.startTime ? form.startTime.substring(0, 16) : '--' }}{{ form.endTime ? form.endTime.substring(0, 16) : '--' }}</text>
</view>
<view class="info-row">
<text class="label">考试地点</text>
<text class="value">{{ form.address || '--' }}</text>
</view>
<view class="info-row">
<text class="label">申请单位</text>
<text class="value">{{ form.memberName || '--' }}</text>
</view>
<view class="info-row">
<text class="label">考官</text>
<text class="value">{{ form.examinerNames || '--' }}</text>
</view>
</view>
</view>
<!-- 考生信息 -->
<view class="card">
<view class="card-header">
<view class="header-left">考生信息</view>
<view class="header-right">{{ list.length }}</view>
</view>
<view v-if="loading" class="state-tip">加载中...</view>
<view v-else-if="list.length === 0" class="state-tip">暂无考生信息</view>
<view class="student-list" v-else>
<view class="student-card" v-for="n in list" :key="n.id">
<view class="student-top">
<view class="student-name">
<text class="name">{{ n.realName || '--' }}</text>
</view>
<view class="score-tag" :class="n.isPass == 1 ? 'pass' : 'fail'">
{{ n.isPass == 1 ? '通过' : '未通过' }}
</view>
</view>
<view class="student-info">
<view class="info-col">
<text class="info-text">{{ n.idcCode || '--' }}</text>
</view>
<view class="info-col">
<text class="info-text">{{ !n.levelOld || n.levelOld == 0 ? '十' : szToHz(n.levelOld) }}</text>
</view>
<view class="info-col">
<text class="info-text">{{ n.levelNew ? szToHz(n.levelNew) + '级' : '--' }}</text>
</view>
<view class="info-col">
<text class="info-text text-red">¥{{ (Number(n.examFee) || 0).toFixed(2) }}</text>
</view>
</view>
</view>
</view>
</view>
<!-- 审核记录 -->
<view class="h3-padding">审核记录</view>
<view class="wBox">
<view v-if="loadingAudit" class="state-tip">加载中...</view>
<view v-else-if="recordList.length === 0" class="state-tip">暂无审核记录</view>
<view class="stepItem" v-else v-for="(n, index) in recordList" :key="index">
<view class="time">{{ n.auditTime || '待审批' }}</view>
<view class="content">
<view class="status">
<text v-if="n.auditResult==1" class="text-success">审核通过</text>
<text v-else-if="n.auditResult==0" class="text-danger">审核拒绝</text>
<text v-else class="text-primary">审核中</text>
</view>
<view class="deptName">{{ n.auditDeptName || '--' }}</view>
<view v-if="n.auditMsg">备注:{{ n.auditMsg }}</view>
</view>
</view>
</view>
</scroll-view>
</view>
</template>
<script setup>
import * as api from '@/common/api.js'
import { szToHz } from '@/common/utils.js'
import { ref } from 'vue'
import { onLoad } from '@dcloudio/uni-app'
const form = ref({})
const list = ref([])
const recordList = ref([])
const loading = ref(false)
const loadingAudit = ref(false)
const selectForm = ref({ pageNum: 1, pageSize: 100 })
let examId = ''
let examType = ref('2')
onLoad((option) => {
examId = option.examId
if (option.type) examType.value = option.type
initData()
})
function initData() {
uni.showLoading({ title: '加载中' })
getForm()
getList()
getRecordList()
}
function getForm() {
api.getExamInfo(examId).then(res => {
uni.hideLoading()
if (res.code === 200 || res.code === 0) {
form.value = res.data || {}
}
}).catch(() => { uni.hideLoading() })
}
function getList() {
loading.value = true
selectForm.value.examId = examId
api.getStudentList(selectForm.value).then(res => {
if (res && res.rows) {
list.value = res.rows
} else {
list.value = []
}
}).catch(() => { list.value = [] }).finally(() => { loading.value = false })
}
function getRecordList() {
loadingAudit.value = true
const typeMap = { '2': 1, '3': 2, '4': 4 }
const logType = typeMap[examType.value] || 1
api.getLogs(examId, logType).then(res => {
if (res && res.data) {
recordList.value = Array.isArray(res.data) ? res.data : (res.data.levelSteps || [])
} else {
recordList.value = []
}
}).catch(() => { recordList.value = [] }).finally(() => { loadingAudit.value = false })
}
</script>
<style scoped lang="scss">
$primary-color: #e8341d;
$success-color: #52c41a;
$danger-color: #e8341c;
$bg-color: #f5f7fa;
$card-bg: #ffffff;
$text-primary: #333;
$text-placeholder: #999;
$border-color: #eee;
$content-gap: 24rpx;
.detail-content {
padding: 20rpx;
background: $bg-color;
min-height: 100vh;
box-sizing: border-box;
}
.h3-padding {
padding: 30rpx 30rpx 0;
font-size: 30rpx;
font-weight: 600;
color: #333;
}
.wBox {
width: 700rpx;
padding: 30rpx;
margin: 20rpx auto 0;
background: #FFFFFF;
box-shadow: 0rpx 12rpx 116rpx 0rpx rgba(196, 203, 214, 0.1);
border-radius: 15rpx;
}
.stepItem {
display: flex;
padding: 16rpx 0;
border-bottom: 1rpx dashed #eee;
&:last-child {
border-bottom: none;
}
.time {
width: 160rpx;
font-size: 22rpx;
color: #999;
flex-shrink: 0;
padding-top: 4rpx;
}
.content {
flex: 1;
.status {
font-size: 28rpx;
font-weight: 600;
margin-bottom: 6rpx;
}
.deptName {
font-size: 26rpx;
color: #666;
}
view {
font-size: 24rpx;
color: #999;
margin-top: 4rpx;
}
}
}
.card {
background: $card-bg;
border-radius: 16rpx;
margin-bottom: 20rpx;
overflow: hidden;
box-shadow: 0 4rpx 12rpx rgba(0, 0, 0, 0.05);
}
.card-header {
display: flex;
justify-content: space-between;
align-items: center;
padding: 24rpx $content-gap 20rpx;
border-bottom: 1rpx solid $border-color;
.header-left {
font-size: 30rpx;
font-weight: 600;
color: $text-primary;
}
.header-right {
font-size: 26rpx;
color: $primary-color;
font-weight: 500;
}
}
.card-body {
padding: 8rpx $content-gap 24rpx;
}
.info-row {
display: flex;
justify-content: space-between;
align-items: center;
padding: 18rpx 0;
border-bottom: 1rpx solid #f5f5f5;
&:last-child {
border-bottom: none;
}
.label {
font-size: 28rpx;
color: $text-placeholder;
flex-shrink: 0;
width: 170rpx;
}
.value {
font-size: 28rpx;
color: $text-primary;
text-align: right;
flex: 1;
word-break: break-all;
padding-left: 10rpx;
}
}
.state-tip {
text-align: center;
padding: 60rpx 0;
font-size: 26rpx;
color: $text-placeholder;
}
.student-list {
padding: 0 $content-gap 24rpx;
}
.student-card {
border-radius: 12rpx;
padding: 24rpx;
margin-top: 16rpx;
border: 1rpx solid $border-color;
.student-top {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 20rpx;
.student-name .name {
font-size: 32rpx;
font-weight: 600;
color: $text-primary;
}
}
.student-info {
display: flex;
justify-content: space-between;
align-items: center;
gap: 12rpx;
.info-col {
flex: 1;
text-align: center;
.info-text {
font-size: 28rpx;
color: $text-primary;
font-weight: 500;
line-height: 1.4;
}
}
}
}
.score-tag {
font-size: 24rpx;
padding: 6rpx 16rpx;
border-radius: 20rpx;
flex-shrink: 0;
font-weight: 500;
&.pass {
background: rgba($success-color, 0.1);
color: $success-color;
border: 1rpx solid rgba($success-color, 0.2);
}
&.fail {
background: rgba($danger-color, 0.1);
color: $danger-color;
border: 1rpx solid rgba($danger-color, 0.2);
}
}
.text-red {
color: $danger-color !important;
}
</style>
......@@ -54,7 +54,8 @@
<view class="content">
<view class="status">
<text v-if="n.auditResult==1" class="text-success">审核通过</text>
<text v-if="n.auditResult==0" class="text-danger">审核拒绝</text>
<text v-else-if="n.auditResult==0" class="text-danger">审核拒绝</text>
<text v-else class="text-primary">审核中</text>
</view>
<view class="deptName">{{ n.auditDeptName || '--' }}</view>
<view v-if="n.auditMsg">备注:{{ n.auditMsg }}</view>
......
Styling with Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!