Files
zhxg_app/pages/finance/knzzZsg/apply.vue

1581 lines
46 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<!-- finance/knzzZsg/apply.vue -->
<template>
<view class="app-container">
<!-- 顶部导航栏 -->
<!-- <view class="nav-bar" @click="goBack">
<uni-icons type="back" size="20" color="#fff"></uni-icons>
<text class="nav-title">中升高困难补助申请</text>
</view> -->
<!-- 选项卡容器 -->
<view class="tabs-container">
<view class="tabs-header">
<view class="tab-item" :class="{ active: activeTab === 0 }" @click="switchTab(0)">
<uni-icons type="contact" size="12" :color="activeTab === 0 ? '#409EFF' : '#666'"></uni-icons>
<text class="tab-text">基本信息</text>
</view>
<view class="tab-item" :class="{ active: activeTab === 1 }" @click="switchTab(1)">
<uni-icons type="home" size="12" :color="activeTab === 1 ? '#409EFF' : '#666'"></uni-icons>
<text class="tab-text">家庭经济情况</text>
</view>
<view class="tab-item" :class="{ active: activeTab === 2 }" @click="switchTab(2)">
<uni-icons type="team" size="12" :color="activeTab === 2 ? '#409EFF' : '#666'"></uni-icons>
<text class="tab-text">家庭成员情况</text>
</view>
<view class="tab-item" :class="{ active: activeTab === 3 }" @click="switchTab(3)">
<uni-icons type="compose" size="12" :color="activeTab === 3 ? '#409EFF' : '#666'"></uni-icons>
<text class="tab-text">申请理由</text>
</view>
<view class="tab-item" :class="{ active: activeTab === 4 }" @click="switchTab(4)">
<uni-icons type="chat" size="12" :color="activeTab === 4 ? '#409EFF' : '#666'"></uni-icons>
<text class="tab-text">审核意见</text>
</view>
</view>
</view>
<!-- 表单内容区域 -->
<scroll-view scroll-y class="form-scroll" :style="{ height: formScrollHeight }">
<view class="form-wrapper">
<!-- 1. 基本信息标签页 -->
<view v-show="activeTab === 0" class="tab-panel">
<view class="form-card">
<view class="card-title">学生基本信息</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>学号</label>
<input v-model="formData.xh" placeholder="请输入学号" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>姓名</label>
<input v-model="formData.xm" placeholder="请输入姓名" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>性别</label>
<picker mode="selector" :range="genderOptions" :range-key="'text'" v-model="formData.xb" @change="handleGenderChange" :disabled="detailMode">
<view class="picker-input">
{{ formData.xb ? getGenderText(formData.xb) : '请选择性别' }}
</view>
</picker>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>学院</label>
<input v-model="formData.xy" placeholder="请输入学院" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>班级</label>
<input v-model="formData.bj" placeholder="请输入班级" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>身份证号</label>
<input v-model="formData.sfzhm" placeholder="请输入身份证号" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>民族</label>
<input v-model="formData.mz" placeholder="请输入民族" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>联系电话</label>
<input v-model="formData.phone" placeholder="请输入联系电话" class="form-input" type="number" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>出生年月</label>
<input v-model="formData.birthMonth" placeholder="请输入出生年月" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>政治面貌</label>
<input v-model="formData.zzmm" placeholder="请输入政治面貌" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>入学时间</label>
<input v-model="formData.inTime" placeholder="请输入入学时间" class="form-input" :disabled="detailMode"></input>
</view>
</view>
<view class="form-card">
<view class="card-title">银行卡信息</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>银行卡号</label>
<input v-model="formData.bankCard" placeholder="请输入银行卡号" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>开户行</label>
<input v-model="formData.bankAddr" placeholder="请输入开户行" class="form-input" :disabled="detailMode"></input>
</view>
</view>
<view class="form-card">
<view class="card-title">就读信息</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>入学前就读的中职学校</label>
<textarea v-model="formData.zzxx" placeholder="请输入入学前就读的中职学校" class="form-textarea" :disabled="detailMode"></textarea>
</view>
</view>
</view>
<!-- 2. 家庭经济情况标签页 -->
<view v-show="activeTab === 1" class="tab-panel">
<view class="form-card">
<view class="card-title">家庭经济情况</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>家庭户口</label>
<picker mode="selector" :range="householdOptions" :range-key="'text'" v-model="formData.jthk" @change="handleHouseholdChange" :disabled="detailMode">
<view class="picker-input">
{{ formData.jthk ? getHouseholdText(formData.jthk) : '请选择家庭户口' }}
</view>
</picker>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>家庭人口数</label>
<input v-model="formData.familyNum" placeholder="请输入家庭人口数" class="form-input" type="number" @input="handleFamilyNumInput" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>家庭月收入</label>
<input v-model="formData.monthMoney" placeholder="请输入家庭月收入" class="form-input" type="number" @input="calculatePerCapitaIncome" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>人均月收入</label>
<input v-model="formData.perMoney" placeholder="自动计算" class="form-input" readonly :disabled="true"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>收入来源</label>
<input v-model="formData.moneySrc" placeholder="请输入收入来源" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>家庭住址</label>
<input v-model="formData.homeAddr" placeholder="请输入家庭住址" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label">邮政编码</label>
<input v-model="formData.postCode" placeholder="请输入邮政编码" class="form-input" type="number" :disabled="detailMode"></input>
</view>
</view>
</view>
<!-- 3. 家庭成员情况标签页 -->
<view v-show="activeTab === 2" class="tab-panel">
<view class="form-card">
<view class="card-title">家庭成员情况</view>
<view class="family-list">
<view v-for="(member, index) in formData.familyMembers" :key="index" class="family-item">
<view class="item-header">
<text class="item-title">家庭成员 {{ index + 1 }}</text>
<uni-icons type="close" size="20" color="#ff4d4f" @click="deleteFamilyMember(index)" class="delete-btn" v-if="!detailMode"></uni-icons>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>姓名</label>
<input v-model="member.familyName" placeholder="请输入姓名" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>年龄</label>
<input v-model="member.age" placeholder="请输入年龄" class="form-input" type="number" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>与学生关系</label>
<input v-model="member.familyRelation" placeholder="请输入与学生关系" class="form-input" :disabled="detailMode"></input>
</view>
<view class="form-item">
<label class="form-label">工作单位</label>
<input v-model="member.workPlace" placeholder="请输入工作单位" class="form-input" :disabled="detailMode"></input>
</view>
</view>
</view>
<view class="add-family-btn" @click="addFamilyMember" v-if="!detailMode">
<uni-icons type="plus" size="20" color="#409EFF"></uni-icons>
<text>新增家庭成员</text>
</view>
</view>
</view>
<!-- 4. 申请理由标签页 -->
<view v-show="activeTab === 3" class="tab-panel">
<view class="form-card">
<view class="card-title">申请理由</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>申请理由</label>
<view class="apply-reason-content">
<view class="reason-intro">
<text>本人基于如下第</text>
<input v-model="formData.applyReasonNum" type="text" class="reason-number-input" placeholder="请输入" :disabled="detailMode"></input>
<text>种原因,符合学费补助申请条件,特提出申请,请审核.</text>
</view>
<view class="reason-options">
<!-- 第一点申请理由作为静态展示 -->
<view class="reason-option">
<view class="option-header">
<text class="option-text">1.监测对象家庭学生(脱贫不稳定家庭学生边缘易致贫家庭学生突发严重困难家庭学生):</text>
</view>
<!-- 子选项仍然可以选择 -->
<view class="sub-options">
<view class="checkbox-item" v-for="(subOption, subIndex) in monitorSubOptions" :key="subIndex" @click="!detailMode && selectMonitorSubOption(subOption.value)">
<view class="custom-checkbox" :class="{ 'checkbox-checked': formData.applyReason1 === subOption.value }">{{ formData.applyReason1 === subOption.value ? '✓' : '' }}</view>
<text class="checkbox-text">{{ subOption.text }}</text>
</view>
</view>
</view>
<!-- 其他申请理由仍然可以选择 -->
<view class="reason-option" v-for="(option, index) in applyReasonOptions" :key="index" v-if="option.value !== '1'">
<view class="option-header" @click="!detailMode && selectApplyReason(option.text)">
<view class="custom-checkbox" :class="{ 'checkbox-checked': formData.applyReason === option.text }">{{ formData.applyReason === option.text ? '✓' : '' }}</view>
<text class="option-text">{{ option.text }}</text>
</view>
</view>
</view>
</view>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>申请理由补充说明(填写):</label>
<textarea v-model="formData.applyReasonExtra" placeholder="请详细描述申请理由" class="form-textarea" rows="4" :disabled="detailMode"></textarea>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>申请人签名</label>
<view class="sign-img" v-if="signImg">
<image :src="signImg" mode="aspectFit" style="width: 200px; height: 50px; cursor: pointer;" @tap="previewSign"></image>
<text @tap="signToggle" class="re-sign-text" v-if="!detailMode">重新签名</text>
</view>
<view v-else class="sign" @tap="signToggle" :class="{ 'sign-disabled': detailMode }">
点击签名
</view>
</view>
<view class="form-item">
<label class="form-label"><span class="red-tip">*</span>中职毕业证</label>
<view class="upload-btn" @click="handleDiplomaUpload" :class="{ 'upload-disabled': detailMode }">
<text class="upload-icon">+</text>
<text>{{ detailMode ? '已上传中职毕业证' : '上传文件' }}</text>
</view>
<view class="file-list" v-if="diplomaFiles.length">
<view class="file-item" v-for="(file, index) in diplomaFiles" :key="index">
<text class="file-name" @click="previewImage(baseUrl + '/' + file.savePath)">{{ file.attachmentName || file.trueName }}</text>
<uni-icons type="trash-filled" size="30" @click="deleteDiplomaFile(index)" v-if="!detailMode" class="delete-btn"></uni-icons>
</view>
</view>
<view class="upload-tip" v-if="!detailMode">支持上传pdf格式文件单个文件不超过10MB</view>
</view>
</view>
</view>
<!-- 5. 审核意见标签页 -->
<view v-show="activeTab === 4" class="tab-panel">
<view class="form-card">
<view class="card-title">审核意见</view>
<!-- 辅导员审核意见 -->
<view class="approval-section">
<view class="section-title">辅导员意见</view>
<view class="approval-content">
<text v-if="formData.fdyCmt" class="approval-text">{{ formData.fdyCmt }}</text>
<text v-else class="no-content">暂无审核意见</text>
</view>
<view class="approval-info">
<text v-if="formData.fdyName">审核人{{ formData.fdyName }}</text>
<text v-if="formData.fdyDate">审核时间{{ formData.fdyDate }}</text>
</view>
</view>
<!-- 学院审核意见 -->
<view class="approval-section">
<view class="section-title">二级学院意见</view>
<view class="approval-content">
<text v-if="formData.deptCmt" class="approval-text">{{ formData.deptCmt }}</text>
<text v-else class="no-content">暂无审核意见</text>
</view>
<view class="approval-info">
<text v-if="formData.xwName">审核人{{ formData.xwName }}</text>
<text v-if="formData.deptDate">审核时间{{ formData.deptDate }}</text>
</view>
</view>
<!-- 学校意见 -->
<view class="approval-section">
<view class="section-title">学校意见</view>
<view class="approval-content">
<text v-if="formData.xgCmt" class="approval-text">{{ formData.xgCmt }}</text>
<text v-else class="no-content">暂无审核意见</text>
</view>
<view class="approval-info">
<text v-if="formData.xgName">审核人{{ formData.xgName }}</text>
<text v-if="formData.xgDate">审核时间{{ formData.xgDate }}</text>
</view>
</view>
</view>
</view>
</view>
</scroll-view>
<!-- 提交按钮 -->
<view class="submit-btn-container" v-if="!detailMode">
<view class="submit-btn" @click="submitApply">
<text>提交申请</text>
</view>
</view>
<!-- 签名组件 -->
<jp-signature-popup ref="jpSignature" :required="true" popup @change="uploadSign" />
</view>
</template>
<script>
import { add, update, reApply, getOwnSign, getOwnFamily, getStudentInfo, getExtraInfo } from '@/api/finance/knzzZsg';
import uploadFile from "@/plugins/upload.js"
import { getUserProfile } from '@/api/system/user'
import config from '@/config'
export default {
data() {
return {
activeTab: 0,
detailMode: false,
formScrollHeight: '',
signImg: '',
baseUrl: config.baseUrl || '',
diplomaFiles: [],
diplomaAffixId: '',
genderOptions: [
{ value: '1', text: '男' },
{ value: '2', text: '女' }
],
householdOptions: [
{ value: '城镇', text: '城镇' },
{ value: '农村', text: '农村' }
],
applyReasonOptions: [
{ value: '1', text: '1.监测对象家庭学生(脱贫不稳定家庭学生、边缘易致贫家庭学生、突发严重困难家庭学生):' },
{ value: '2', text: '2.城乡低保家庭学生;' },
{ value: '3', text: '3.特困救助供养家庭学生;' },
{ value: '4', text: '4.孤儿(含事实无人抚养儿童);' },
{ value: '5', text: '5.脱贫家庭学生(原建档立卡学生);' },
{ value: '6', text: '6.家庭经济困难残疾学生;' },
{ value: '7', text: '7.因重大自然灾害、重大事故和重大疾病等导致家庭经济困难的学生;' },
{ value: '8', text: '8.其他家庭经济困难因素.' }
],
monitorSubOptions: [
{ value: '未消除风险;', text: '未消除风险;' },
{ value: '已消除风险;', text: '已消除风险;' }
],
formData: {
// 基本信息
xh: '',
xm: '',
xb: '',
xy: '',
bj: '',
sfzhm: '',
mz: '',
phone: '',
birthMonth: '',
zzmm: '',
inTime: '',
// 银行卡信息
bankCard: '',
bankAddr: '',
// 就读信息
zzxx: '',
// 家庭经济情况
jthk: '',
familyNum: '',
monthMoney: '',
perMoney: '',
moneySrc: '',
homeAddr: '',
postCode: '',
// 家庭成员情况
familyMembers: [
{
familyName: '',
age: '',
familyRelation: '',
workPlace: ''
}
],
// 申请理由
applyReasonNum: '',
applyReason: '',
applyReason1: '',
applyReasonExtra: '',
// 签名信息
applySign: ''
}
};
},
onLoad(options) {
this.calculateFormScrollHeight();
uni.getSystemInfo({
success: (res) => {
this.formScrollHeight = `${res.windowHeight - 200}px`;
}
});
const { id, type } = options || {};
this.detailMode = type === 'detail';
// 如果有id参数尝试从本地存储获取传递的数据
if (id) {
const item = uni.getStorageSync('knzzZsgItem');
if (item) {
// 使用传递的数据填充表单
this.fillFormData(item);
return;
}
}
// 页面加载时调用API获取学生信息
this.loadStudentInfo();
},
methods: {
// 加载学生信息
loadStudentInfo() {
uni.showLoading({ title: '加载中...' });
// 并行调用多个API接口
Promise.all([
getUserProfile(),
getOwnFamily(),
getStudentInfo(),
getExtraInfo()
]).then(([userProfileRes, familyRes, studentRes, extraRes]) => {
uni.hideLoading();
// 处理学生基本信息
if (studentRes.code === 200 && studentRes.data) {
const studentInfo = studentRes.data;
this.formData.xh = studentInfo.stuNo || '';
this.formData.xm = studentInfo.name || '';
// 处理性别字段将文本转换为value值
if (studentInfo.gender === '男') {
this.formData.xb = '1';
} else if (studentInfo.gender === '女') {
this.formData.xb = '2';
} else {
this.formData.xb = '';
}
this.formData.xy = studentInfo.dept ? studentInfo.dept.deptName : '';
this.formData.bj = studentInfo.srsClass ? studentInfo.srsClass.className : '';
this.formData.sfzhm = studentInfo.idCard || '';
this.formData.phone = studentInfo.phone || '';
this.formData.birthMonth = studentInfo.birthday ? this.formatBirthday(studentInfo.birthday) : '';
this.formData.bankCard = studentInfo.xhk || '';
this.formData.bankAddr = studentInfo.bankAddr || '';
}
// 处理学生额外信息
if (extraRes.code === 200 && extraRes.data) {
const extraInfo = extraRes.data;
this.formData.mz = extraInfo.mz || '';
this.formData.zzmm = extraInfo.zzmm || '';
// 处理家庭户口字段
this.formData.jthk = extraInfo.hkxz || '';
this.formData.homeAddr = extraInfo.xjtdz || '';
this.formData.postCode = extraInfo.jtyzbm || '';
}
// 处理家庭成员信息
if (familyRes.code === 200 && familyRes.data) {
const familyData = familyRes.data;
// 检查返回的数据是否是数组
if (Array.isArray(familyData) && familyData.length > 0) {
// 转换家庭成员数据格式,只保留需要的字段
this.formData.familyMembers = familyData.map(member => ({
familyName: member.familyName || '',
age: member.age || '',
familyRelation: member.familyRelation || '',
workPlace: member.workPlace || ''
}));
}
}
// 处理签名信息
if (userProfileRes.code === 200 && userProfileRes.data && userProfileRes.data.signature) {
this.formData.applySign = userProfileRes.data.signature;
this.signImg = this.baseUrl + userProfileRes.data.signature;
}
}).catch(err => {
uni.hideLoading();
uni.showToast({
title: '网络错误,获取学生信息失败',
icon: 'none'
});
});
},
// 处理家庭人口数输入,确保只能输入正整数
handleFamilyNumInput() {
// 移除非数字字符
this.formData.familyNum = this.formData.familyNum.replace(/[^0-9]/g, '');
// 确保输入值大于0
if (parseInt(this.formData.familyNum) <= 0) {
this.formData.familyNum = '';
}
// 重新计算人均月收入
this.calculatePerCapitaIncome();
},
// 格式化生日日期
formatBirthday(birthday) {
if (!birthday) return '';
// 假设birthday是YYYY-MM-DD格式的字符串
const date = new Date(birthday);
const year = date.getFullYear();
const month = date.getMonth() + 1;
return `${year}${month}`;
},
// 填充表单数据
fillFormData(item) {
// 设置申请ID用于判断是新增还是修改
this.formData.id = item.id || '';
// 设置申请状态,用于判断是否为重新提交
this.formData.applyStatus = item.applyStatus || '';
// 基本信息
this.formData.xh = item.stuNo || '';
this.formData.xm = item.stuName || '';
// 处理性别字段将文本转换为value值
if (item.gender === '男') {
this.formData.xb = '1';
} else if (item.gender === '女') {
this.formData.xb = '2';
} else {
this.formData.xb = '';
}
this.formData.xy = item.deptName || '';
this.formData.bj = item.className || '';
this.formData.sfzhm = item.idCard || '';
this.formData.phone = item.stuPhone || '';
this.formData.birthMonth = item.birthMonth || '';
this.formData.mz = item.mz || '';
this.formData.zzmm = item.zzmm || '';
this.formData.inTime = item.inTime || '';
// 银行卡信息
this.formData.bankCard = item.bankCard || '';
this.formData.bankAddr = item.bankAddr || '';
// 就读信息
this.formData.zzxx = item.zzxx || '';
// 家庭经济情况
this.formData.jthk = item.jthk || '';
this.formData.familyNum = item.familyNum || '';
this.formData.monthMoney = item.monthMoney || '';
this.formData.perMoney = item.perMoney || '';
this.formData.moneySrc = item.moneySrc || '';
this.formData.homeAddr = item.homeAddr || '';
this.formData.postCode = item.postCode || '';
// 家庭成员情况
if (item.familyMemberList) {
try {
const familyMembers = JSON.parse(item.familyMemberList);
if (Array.isArray(familyMembers)) {
this.formData.familyMembers = familyMembers;
}
} catch (e) {
console.error('解析家庭成员数据失败:', e);
}
}
// 申请理由
this.formData.applyReasonNum = item.applyReasonNum || '';
this.formData.applyReason = item.applyReason || '';
this.formData.applyReason1 = item.applyReason1 || '';
this.formData.applyReasonExtra = item.applyExtraReason || '';
// 签名和文件信息
this.formData.applySign = item.applySign || '';
this.formData.diplomaFile = item.diplomaCertificate || '';
// 构造完整的签名图片URL
this.signImg = item.applySign ? this.getFullImageUrl(item.applySign) : '';
console.log('处理签名图片item.applySign:', item.applySign);
console.log('signImg:', this.signImg);
// 审核意见
this.formData.fdyCmt = item.fdyCmt || '';
this.formData.fdyName = item.fdyName || '';
this.formData.fdyDate = item.fdyDate || '';
this.formData.deptCmt = item.xwCmt || '';
this.formData.xwName = item.xwName || '';
this.formData.deptDate = item.xwDate || '';
this.formData.xgCmt = item.xgCmt || '';
this.formData.xgName = item.xgName || '';
this.formData.xgDate = item.xgDate || '';
// 处理中职毕业证文件
if (item.diplomaCertificate) {
const fileName = item.diplomaCertificate.substring(item.diplomaCertificate.lastIndexOf('/') + 1);
this.diplomaFiles = [{
attachmentName: fileName,
attachmentUrl: item.diplomaCertificate,
serverUrl: item.diplomaCertificate,
savePath: item.diplomaCertificate
}];
}
},
// 计算表单滚动区域高度
calculateFormScrollHeight() {
uni.getSystemInfo({
success: (res) => {
this.formScrollHeight = `${res.windowHeight - 200}px`;
}
});
},
// 切换选项卡
switchTab(index) {
this.activeTab = index;
},
// 返回上一页
goBack() {
uni.navigateBack();
},
// 处理性别选择
handleGenderChange(e) {
this.formData.xb = this.genderOptions[e.detail.value].value;
},
// 获取性别文本
getGenderText(value) {
const option = this.genderOptions.find(opt => opt.value === value);
return option ? option.text : '';
},
// 处理家庭户口选择
handleHouseholdChange(e) {
this.formData.jthk = this.householdOptions[e.detail.value].value;
},
// 获取家庭户口文本
getHouseholdText(value) {
const option = this.householdOptions.find(opt => opt.value === value);
return option ? option.text : '';
},
// 处理申请理由类型选择
selectApplyReason(value) {
// 确保applyReason字段只包含申请理由文本不包含子选项
const reasonText = value.split('未消除风险;')[0].split('已消除风险;')[0];
this.formData.applyReason = reasonText;
// 当选择的不是监测对象家庭学生时清空applyReason1字段
if (value !== '1.监测对象家庭学生(脱贫不稳定家庭学生、边缘易致贫家庭学生、突发严重困难家庭学生):') {
this.formData.applyReason1 = '';
}
},
// 处理监测对象家庭学生子选项选择
selectMonitorSubOption(value) {
this.formData.applyReason1 = value;
// 当选择子选项时将applyReason字段设置为子选项的值
this.formData.applyReason = value;
},
// 获取申请理由类型文本
getApplyReasonText(value) {
const option = this.applyReasonOptions.find(opt => opt.value === value);
return option ? option.text : '';
},
// 计算人均月收入
calculatePerCapitaIncome() {
if (this.formData.familyNum && this.formData.monthMoney) {
const familyNum = parseFloat(this.formData.familyNum);
const monthMoney = parseFloat(this.formData.monthMoney);
if (familyNum > 0) {
this.formData.perMoney = (monthMoney / familyNum).toFixed(2);
} else {
this.formData.perMoney = '0';
}
}
},
// 添加家庭成员
addFamilyMember() {
this.formData.familyMembers.push({
familyName: '',
age: '',
familyRelation: '',
workPlace: ''
});
},
// 删除家庭成员
deleteFamilyMember(index) {
if (this.formData.familyMembers.length > 1) {
this.formData.familyMembers.splice(index, 1);
} else {
uni.showToast({
title: '至少需要保留一个家庭成员',
icon: 'none'
});
}
},
// 验证表单
validateForm() {
// 基本信息验证
if (!this.formData.xh) {
uni.showToast({ title: '请输入学号', icon: 'none' });
return false;
}
if (!this.formData.xm) {
uni.showToast({ title: '请输入姓名', icon: 'none' });
return false;
}
if (!this.formData.xb) {
uni.showToast({ title: '请选择性别', icon: 'none' });
return false;
}
if (!this.formData.xy) {
uni.showToast({ title: '请输入学院', icon: 'none' });
return false;
}
if (!this.formData.bankCard) {
uni.showToast({ title: '请输入银行卡号', icon: 'none' });
return false;
}
if (!this.formData.bankAddr) {
uni.showToast({ title: '请输入开户行', icon: 'none' });
return false;
}
if (!this.formData.zzxx) {
uni.showToast({ title: '请输入入学前就读的中职学校', icon: 'none' });
return false;
}
// 家庭经济情况验证
if (!this.formData.jthk) {
uni.showToast({ title: '请选择家庭户口', icon: 'none' });
return false;
}
if (!this.formData.familyNum) {
uni.showToast({ title: '请输入家庭人口数', icon: 'none' });
return false;
}
if (!this.formData.monthMoney) {
uni.showToast({ title: '请输入家庭月收入', icon: 'none' });
return false;
}
// 家庭成员情况验证
for (let i = 0; i < this.formData.familyMembers.length; i++) {
const member = this.formData.familyMembers[i];
if (!member.familyName) {
uni.showToast({ title: `请输入家庭成员${i + 1}的姓名`, icon: 'none' });
return false;
}
if (!member.age) {
uni.showToast({ title: `请输入家庭成员${i + 1}的年龄`, icon: 'none' });
return false;
}
if (!member.familyRelation) {
uni.showToast({ title: `请输入家庭成员${i + 1}与学生的关系`, icon: 'none' });
return false;
}
}
// 申请理由验证
if (!this.formData.applyReasonNum) {
uni.showToast({ title: '请输入申请理由序号', icon: 'none' });
return false;
}
if (!this.formData.applyReason) {
uni.showToast({ title: '请选择申请理由', icon: 'none' });
return false;
}
if (this.formData.applyReason === '1.监测对象家庭学生(脱贫不稳定家庭学生、边缘易致贫家庭学生、突发严重困难家庭学生):' && !this.formData.applyReason1) {
uni.showToast({ title: '请选择监测对象家庭学生子选项', icon: 'none' });
return false;
}
if (!this.formData.applyReasonExtra) {
uni.showToast({ title: '请输入申请理由补充说明', icon: 'none' });
return false;
}
// 申请人签名验证
if (!this.formData.applySign) {
uni.showToast({ title: '请上传申请人签名', icon: 'none' });
return false;
}
// 中职毕业证验证
if (!this.formData.diplomaFile) {
uni.showToast({ title: '请上传中职毕业证', icon: 'none' });
return false;
}
return true;
},
// 打开签名对话框
signToggle() {
// 打开签名组件
this.$refs.jpSignature.toPop();
},
// 上传签名
uploadSign(e) {
uploadFile('/common/upload', e).then((res) => {
const data = JSON.parse(res);
this.formData.applySign = data.fileName;
this.signImg = data.url || this.getFullImageUrl(data.fileName);
})
},
// 获取完整图片URL
getFullImageUrl(path) {
if (!path) return '';
// 调试信息
console.log('getFullImageUrl调用path:', path);
// 如果已经是完整URL则直接返回
if (path.startsWith('http://') || path.startsWith('https://')) {
return path;
}
// 使用配置文件中的baseUrl
const currentBaseUrl = config.baseUrl || '';
console.log('当前baseUrl:', currentBaseUrl);
// 处理baseUrl确保结尾没有斜杠
const baseUrlClean = currentBaseUrl.replace(/\/$/, '');
// 处理path确保开头没有斜杠
const pathClean = path.replace(/^\//, '');
// 拼接URL
const fullUrl = `${baseUrlClean}/${pathClean}`;
console.log('拼接后的完整URL:', fullUrl);
return fullUrl;
},
// 预览签名图片
previewSign() {
if (this.signImg) {
uni.previewImage({
urls: [this.signImg]
});
}
},
// 处理中职毕业证上传
handleDiplomaUpload() {
if (this.detailMode) {
return;
}
const generateUUID = () => {
return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
const r = Math.random() * 16 | 0;
const v = c === 'x' ? r : (r & 0x3 | 0x8);
return v.toString(16);
});
};
uni.chooseFile({
count: 1, // 只允许上传一个文件
extension: ['.pdf'],
success: async (chooseRes) => {
if (!this.diplomaAffixId) {
this.diplomaAffixId = generateUUID();
}
for (const file of chooseRes.tempFiles) {
try {
const formDataObj = {
affixId: this.diplomaAffixId,
fileName: file.name,
fileSize: file.size
};
const uploadRes = await uploadFile('/affix/upload', file.path, formDataObj);
const result = typeof uploadRes === 'string' ? JSON.parse(uploadRes) : uploadRes;
if (result && result.code === 200) {
const fileInfo = {
attachmentName: file.name,
attachmentUrl: result.savePath,
serverUrl: result.savePath || '',
fileId: result.id || '',
fileSize: file.size,
fileSuffix: file.name.split('.').pop().toLowerCase(),
savePath: result.savePath
};
const isDuplicate = this.diplomaFiles.some(item =>
item.attachmentName === file.name && item.fileSize === file.size
);
if (!isDuplicate) {
this.diplomaFiles.push(fileInfo);
this.formData.diplomaFile = result.savePath;
}
uni.showToast({
title: `文件 ${file.name} 上传成功`,
icon: 'success',
duration: 1500
});
} else {
uni.showToast({
title: `文件 ${file.name} 上传失败:${result.message || '未知错误'}`,
icon: 'none',
duration: 2000
});
}
} catch (error) {
console.error(`文件 ${file.name} 上传异常:`, error);
uni.showToast({
title: `文件 ${file.name} 上传异常,请重试`,
icon: 'none',
duration: 2000
});
}
}
},
fail: (err) => {
console.error('选择文件失败:', err);
uni.showToast({
title: '选择文件失败,请重试',
icon: 'none'
});
}
});
},
// 删除中职毕业证文件
deleteDiplomaFile(index) {
const deletedFile = this.diplomaFiles[index];
this.diplomaFiles.splice(index, 1);
if (this.diplomaFiles.length === 0) {
this.diplomaAffixId = null;
this.formData.diplomaFile = null;
}
uni.showToast({
title: '删除成功',
icon: 'success'
});
},
// 预览图片
previewImage(url) {
uni.previewImage({
urls: [url]
});
},
// 提交申请
submitApply() {
if (!this.validateForm()) {
return;
}
uni.showLoading({ title: '提交中...' });
// 准备提交数据,确保字段名称与后端一致
const submitData = {
// 申请ID修改时需要提交
id: this.formData.id || '',
// 基本信息
stuNo: this.formData.xh || '',
stuName: this.formData.xm || '',
gender: this.getGenderText(this.formData.xb) || '',
birthMonth: this.formData.birthMonth || '',
mz: this.formData.mz || '',
zzmm: this.formData.zzmm || '',
inTime: this.formData.inTime || '',
idCard: this.formData.sfzhm || '',
stuPhone: this.formData.phone || '',
// 银行卡信息
bankCard: this.formData.bankCard || '',
bankAddr: this.formData.bankAddr || '',
// 就读信息
zzxx: this.formData.zzxx || '',
deptName: this.formData.xy || '',
className: this.formData.bj || '',
// 家庭经济情况
jthk: this.formData.jthk || '',
familyNum: this.formData.familyNum || '',
monthMoney: this.formData.monthMoney || '',
perMoney: this.formData.perMoney || '',
moneySrc: this.formData.moneySrc || '',
homeAddr: this.formData.homeAddr || '',
postCode: this.formData.postCode || '',
// 家庭成员情况
familyMemberList: JSON.stringify(this.formData.familyMembers) || '',
// 申请理由
applyReasonNum: this.formData.applyReasonNum || '',
applyReason: this.formData.applyReason || '',
applyReason1: this.formData.applyReason1 || '',
applyExtraReason: this.formData.applyReasonExtra || '',
// 签名和文件信息
applySign: this.formData.applySign || '',
diplomaCertificate: this.formData.diplomaFile || ''
};
// 调用接口提交申请
let submitApi;
// 如果是已驳回状态10使用重新提交接口
if (this.formData.applyStatus === '10') {
submitApi = reApply;
} else {
// 否则根据是否有ID判断使用修改还是新增接口
submitApi = this.formData.id ? update : add;
}
submitApi(submitData).then(res => {
uni.hideLoading();
if (res.code === 200) {
uni.showToast({
title: '申请提交成功',
icon: 'success'
});
// 跳转到列表页面
setTimeout(() => {
uni.navigateTo({
url: '/pages/finance/knzzZsg/index'
});
}, 1500);
} else {
uni.showToast({
title: res.msg || '申请提交失败',
icon: 'none'
});
}
}).catch(err => {
uni.hideLoading();
uni.showToast({
title: '网络错误,请稍后重试',
icon: 'none'
});
});
}
}
};
</script>
<style lang="less" scoped>
.app-container {
width: 100%;
min-height: 100vh;
background-color: #F3F4F6;
}
/* 顶部导航栏 */
.nav-bar {
background-color: #4A90E2;
color: white;
padding: 20rpx;
display: flex;
align-items: center;
position: sticky;
top: 0;
z-index: 100;
.nav-title {
font-size: 36rpx;
font-weight: bold;
margin-left: 20rpx;
}
}
/* 选项卡容器 */
.tabs-container {
background-color: white;
margin-bottom: 20rpx;
.tabs-header {
display: flex;
flex-wrap: nowrap;
overflow-x: auto;
.tab-item {
display: flex;
flex-direction: column;
align-items: center;
padding: 20rpx 15rpx;
flex: 1;
min-width: 150rpx;
.tab-text {
margin-top: 5rpx;
font-size: 24rpx;
}
&.active {
.tab-text {
color: #409EFF;
font-weight: bold;
}
}
}
}
}
/* 表单滚动区域 */
.form-scroll {
width: 100%;
margin-bottom: 100rpx;
.form-wrapper {
padding: 20rpx;
}
}
/* 标签页面板 */
.tab-panel {
width: 100%;
}
/* 表单卡片 */
.form-card {
background-color: white;
border-radius: 10rpx;
padding: 20rpx;
margin-bottom: 20rpx;
box-shadow: 0 2rpx 10rpx rgba(0, 0, 0, 0.05);
.card-title {
font-size: 32rpx;
font-weight: bold;
margin-bottom: 20rpx;
color: #333;
}
}
/* 表单项目 */
.form-item {
margin-bottom: 20rpx;
.form-label {
display: block;
margin-bottom: 10rpx;
font-size: 28rpx;
color: #666;
}
.form-input {
width: 100%;
height: 80rpx;
border: 1rpx solid #E5E5E5;
border-radius: 5rpx;
padding: 0 20rpx;
font-size: 28rpx;
background-color: #FAFAFA;
}
.form-textarea {
width: 100%;
height: 200rpx;
border: 1rpx solid #E5E5E5;
border-radius: 5rpx;
padding: 15rpx;
font-size: 28rpx;
resize: none;
background-color: #FAFAFA;
}
.picker-input {
width: 100%;
height: 80rpx;
border: 1rpx solid #E5E5E5;
border-radius: 5rpx;
padding: 0 20rpx;
font-size: 28rpx;
background-color: #FAFAFA;
display: flex;
align-items: center;
color: #999;
}
}
/* 红色提示 */
.red-tip {
color: #ff4d4f;
font-size: 28rpx;
}
/* 家庭成员列表 */
.family-list {
margin-top: 10rpx;
.family-item {
background-color: #F9F9F9;
border-radius: 8rpx;
padding: 15rpx;
margin-bottom: 15rpx;
.item-header {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 15rpx;
.item-title {
font-size: 28rpx;
font-weight: bold;
color: #333;
}
}
}
}
/* 添加家庭成员按钮 */
.add-family-btn {
display: flex;
align-items: center;
justify-content: center;
padding: 20rpx;
margin-top: 10rpx;
color: #409EFF;
font-size: 28rpx;
text {
margin-left: 10rpx;
}
}
/* 提交按钮容器 */
.submit-btn-container {
position: fixed;
bottom: 0;
left: 0;
right: 0;
display: flex;
padding: 10px;
background-color: #fff;
border-top: 1px solid #e4e7ed;
z-index: 100;
}
/* 提交按钮 */
.submit-btn {
width: 100%;
height: 40px;
border-radius: 20px;
font-size: 14px;
border: none;
background-color: #409EFF;
color: #fff;
display: flex;
align-items: center;
justify-content: center;
gap: 5px;
}
.submit-primary {
background-color: #67c23a;
}
/* 复选框容器 */
.checkbox-container {
display: flex;
flex-wrap: wrap;
gap: 20rpx;
.checkbox-item {
display: flex;
align-items: center;
cursor: pointer;
transition: all 0.3s ease;
&:hover {
transform: translateY(-2rpx);
}
.custom-checkbox {
width: 30rpx;
height: 30rpx;
border: 1rpx solid #D9D9D9;
border-radius: 50%;
margin-right: 10rpx;
display: flex;
align-items: center;
justify-content: center;
font-size: 20rpx;
color: #fff;
transition: all 0.3s ease;
&.checkbox-checked {
background-color: #409EFF;
border-color: #409EFF;
animation: checkboxScale 0.3s ease-in-out;
}
}
.checkbox-text {
font-size: 26rpx;
color: #666;
}
}
}
/* 复选框动画 */
@keyframes checkboxScale {
0% {
transform: scale(0.8);
}
50% {
transform: scale(1.1);
}
100% {
transform: scale(1);
}
}
/* 申请理由内容 */
.apply-reason-content {
padding: 20rpx;
background-color: #f9f9f9;
border-radius: 10rpx;
}
.reason-intro {
margin-bottom: 20rpx;
line-height: 40rpx;
}
.reason-number-input {
width: 80rpx;
height: 40rpx;
border: 1rpx solid #d9d9d9;
border-radius: 4rpx;
padding: 0 10rpx;
margin: 0 10rpx;
font-size: 28rpx;
}
.reason-options {
margin-top: 20rpx;
}
.reason-option {
margin-bottom: 20rpx;
}
.option-header {
display: flex;
align-items: flex-start;
cursor: pointer;
transition: all 0.3s ease;
&:hover {
transform: translateY(-2rpx);
}
.custom-checkbox {
width: 30rpx;
height: 30rpx;
border: 1rpx solid #D9D9D9;
border-radius: 50%;
margin-top: 8rpx;
margin-right: 15rpx;
display: flex;
align-items: center;
justify-content: center;
font-size: 20rpx;
color: #fff;
transition: all 0.3s ease;
&.checkbox-checked {
background-color: #409EFF;
border-color: #409EFF;
animation: checkboxScale 0.3s ease-in-out;
}
}
.option-text {
flex: 1;
font-size: 26rpx;
color: #333;
line-height: 40rpx;
}
}
.sub-options {
margin-left: 50rpx;
margin-top: 10rpx;
display: flex;
gap: 40rpx;
.checkbox-item {
display: flex;
align-items: center;
cursor: pointer;
transition: all 0.3s ease;
&:hover {
transform: translateY(-2rpx);
}
.custom-checkbox {
width: 30rpx;
height: 30rpx;
border: 1rpx solid #D9D9D9;
border-radius: 50%;
margin-right: 10rpx;
display: flex;
align-items: center;
justify-content: center;
font-size: 20rpx;
color: #fff;
transition: all 0.3s ease;
&.checkbox-checked {
background-color: #409EFF;
border-color: #409EFF;
animation: checkboxScale 0.3s ease-in-out;
}
}
.checkbox-text {
font-size: 26rpx;
color: #666;
}
}
}
/* 签名样式 */
.sign-img {
margin-top: 10rpx;
display: flex;
align-items: center;
gap: 20rpx;
}
.re-sign-text {
color: #409EFF;
font-size: 24rpx;
cursor: pointer;
}
.sign {
margin-top: 10rpx;
width: 200px;
height: 50px;
border: 1rpx solid #d9d9d9;
border-radius: 5rpx;
display: flex;
align-items: center;
justify-content: center;
cursor: pointer;
background-color: #f9f9f9;
color: #666;
font-size: 24rpx;
transition: all 0.3s ease;
&:hover {
border-color: #409EFF;
color: #409EFF;
}
&.sign-disabled {
cursor: not-allowed;
background-color: #f5f5f5;
color: #999;
}
}
/* 审核意见样式 */
.approval-section {
margin-bottom: 30rpx;
.section-title {
font-size: 26rpx;
font-weight: bold;
color: #333;
margin-bottom: 15rpx;
}
.approval-content {
padding: 20rpx;
background-color: #F9F9F9;
border-radius: 10rpx;
margin-bottom: 10rpx;
transition: all 0.3s ease;
&:hover {
background-color: #F0F0F0;
}
.approval-text {
font-size: 24rpx;
color: #666;
line-height: 1.5;
white-space: pre-wrap;
}
.no-content {
font-size: 24rpx;
color: #999;
}
}
.approval-info {
display: flex;
justify-content: space-between;
font-size: 22rpx;
color: #999;
padding: 0 20rpx;
}
}
/* 文件上传样式 */
.upload-btn {
width: 200px;
height: 50px;
border: 1rpx dashed #d9d9d9;
border-radius: 8rpx;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
cursor: pointer;
transition: all 0.3s ease;
&:hover {
border-color: #409EFF;
color: #409EFF;
}
&.upload-disabled {
cursor: not-allowed;
background-color: #f5f5f5;
border-color: #ddd;
color: #999;
}
.upload-icon {
font-size: 36rpx;
font-weight: bold;
margin-bottom: 5rpx;
}
}
.file-list {
margin-top: 20rpx;
.file-item {
display: flex;
justify-content: space-between;
align-items: center;
padding: 15rpx;
background-color: #f9f9f9;
border-radius: 8rpx;
margin-bottom: 10rpx;
.file-name {
flex: 1;
color: #333;
font-size: 24rpx;
word-break: break-all;
margin-right: 20rpx;
cursor: pointer;
}
.delete-btn {
cursor: pointer;
transition: all 0.3s ease;
&:hover {
transform: scale(1.1);
}
}
}
}
.upload-tip {
margin-top: 10rpx;
font-size: 22rpx;
color: #999;
line-height: 1.4;
}
</style>