1. 使用el-form 嵌套 el-table ,利用 el-form 中 rules 校验
代码:
<el-form class="confirm-table" :model="formData" ref="signerConfirmationTableForm">
<el-table :data="formData.devOpsProjectUsageDetails" ref="table" border stripe
:span-method="tableSpanMethod"
style="width: 100%" :cell-style="{borderColor:'#d9dde2'}"
:header-cell-style="{backgroundColor:'#e9eef3',color:'#000',borderColor:'#d9dde2'}"
header-cell-style="width:100%;text-align:center" >
<!-- <el-table-column type="index" width="50"></el-table-column> -->
<el-table-column label="局级单位" prop="parentOrgName" min-width="200" show-overflow-tooltip>
<template slot="header" slot-scope="scope">
<div>
<span style="color: red;">*</span>
<span>局级单位</span>
</div>
</template>
<template slot-scope="scope">
<div>{{scope.row.parentOrgName}}</div>
</template>
</el-table-column>
<el-table-column label="二级单位" prop="orgName" min-width="200" show-overflow-tooltip>
<template slot="header" slot-scope="scope">
<div>
<span style="color: red;">*</span>
<span>二级单位</span>
</div>
</template>
<template slot-scope="scope">
<div>{{scope.row.orgName}}</div>
</template>
</el-table-column>
<!-- 1到12月,对应字段起名叫month1到month12 -->
<el-table-column :label="formData.headerName">
<el-table-column v-for="item in 12" :label="item + '月'" :prop=" `month${item}RegisterCount`"
min-width="160">
<div style="padding-top: 10px;" slot-scope="scope">
<div v-if="scope.row.dataType == 1 || readonly">{{scope.row[`month${item}RegisterCount`]}}</div>
<el-form-item v-else
:prop="`devOpsProjectUsageDetails.${scope.$index}.month${item}RegisterCount`"
:rules="rules.monthResourceRules">
<el-input v-model.trim="scope.row[`month${item}RegisterCount`]" placeholder="输正数保留2位小数" style="width:100%"
@blur="handleMonthDataBlur(scope,item,scope.$index)">
</el-input>
</el-form-item>
</div>
</el-table-column>
</el-table-column>
<el-table-column label="总计" prop="yearTotalCount" min-width="200" show-overflow-tooltip>
<template slot-scope="scope">
{{scope.row.yearTotalCount}}
</template>
</el-table-column>
<el-table-column label="月平均" prop="yearAvgRegisterCount" min-width="200" show-overflow-tooltip>
<template slot-scope="scope">
{{scope.row.yearAvgRegisterCount}}
</template>
</el-table-column>
<el-table-column label="附件" prop="fileList" min-width="500">
<template slot-scope="scope">
<!-- scope.row.dataType 是填报信息 只读 -->
<file-upload v-model="scope.row.fileList" :disabled="scope.row.dataType == 1 || readonly" :drag="false"
:multiple="true"></file-upload>
</template>
</el-table-column>
<!-- 填报详情 -->
<el-table-column label="签认情况">
<el-table-column label="签认状态" prop="flowStatusOption.value" min-width="200" show-overflow-tooltip align="center">
</el-table-column>
<el-table-column label="签认人" prop="signUserName" min-width="200" show-overflow-tooltip align="center">
</el-table-column>
<el-table-column label="联系方式" prop="applyUserPhone" min-width="200" show-overflow-tooltip align="center">
</el-table-column>
<el-table-column label="签认时间" prop="signTime" min-width="200" show-overflow-tooltip align="center">
</el-table-column>
</el-table-column>
</el-table>
</el-form>
var view = {
name: 'info-signer-confirmation',
template: ToolCenter.getTemplate(
'/infoSignerConfirmation/view.html',
'/infoSignerConfirmation/view.css'
),
props: {
visible: {
// dialog是否展示,用watch监听
type: Boolean,
default() {
return true;
}
},
// 列表行数据 或 待办通知进来数据
flowFormData: {
type: Object,
default() {
return {};
}
},
},
data: function () {
// 校验是否和上一行一致
const checkoutResource = (rule, value, callback) => {
if (!value && value != 0) {
return callback(new Error('输入不能为空'));
}
if (isNaN(value)) {
return callback(new Error('请输入正数保留两位小数'));
}
if (Number(value) < 0) {
return callback(new Error('请输入正数保留两位小数'));
}
if (rule.field && this.editDataType === 2) {
let reg = /(?<=devOpsProjectUsageDetails.).*?(?=.month)/;
let index = rule.field.match(reg);
if (
index &&
index.length > 0 &&
!isNaN(parseFloat(index[0]))
) {
index = index[0];
if (index) {
// 获取上一行对比
let diffFieId = rule.field.replaceAll(
'devOpsProjectUsageDetails.' + index + '.',
''
);
let val =
this.formData.devOpsProjectUsageDetails[index - 1][diffFieId];
if (value != val) {
return callback(new Error(' '));
}
}
}
}
callback();
};
return {
readonly: false,
dialogShow: false,
// 模板数据
formData: {
headerName: '', // 表头
devOpsProjectUsageDetails: [] // 表格数据
},
tableData:[],
formData: {}, // 基本信息表单
rules: {
monthResourceRules: [
{
validator: checkoutResource,
required: true,
rowIndex: 0,
trigger: 'blur'
}
]
},
editDataType: 2, // 是否可编辑
};
},
watch: {
},
created: function () {},
mounted: function () {},
methods: {
/**
* 签认校验
* @param {*} dataArr 遍历数据源
* @returns true 不一致 false 一致
*/
checkSignatureData: function(dataArr){
function areFieldsDifferent(arr, index1, index2, fields) {
const obj1 = arr[index1];
const obj2 = arr[index2];
return fields.some(field => obj1.hasOwnProperty(field) && obj2.hasOwnProperty(field) && obj1[field] !== obj2[field]);
}
// 匹配月份填报字段
let fieldsToCompare = []
for(let j=1; j<=12; j++){
fieldsToCompare.push(`month${j}RegisterCount`)
}
let flag = areFieldsDifferent(dataArr,0,1, fieldsToCompare)
if(flag){
DesktopManager.showAlert({
type: 'warning',
content: `数据有异议,退回修改`
});
return true
}
return false
},
validateDataForm(ref, msg) {
return new Promise((resolve, reason) => {
ref.validate((valid) => {
resolve(valid);
});
});
},
// 校验表单
async submitVerifyForm() {
let taskValidateArr = [];
taskValidateArr.push(
this.validateDataForm(
this.$refs.signerConfirmationTableForm,
'请检查表格内容!'
)
);
let res = await Promise.all(taskValidateArr);
return res.every((d) => d === true);
},
// 提交流程校验
flowValidFormData: async function (obj, callback) {
console.log('flowValidFormData ', obj, callback);
this.flowValidForm.obj = obj
this.flowValidForm.callback = callback
/**
* 第一个参数 null/控制loading 1关掉loading
* 第二个参数 下个流程的参数
* callback(1, { userList: [{}] });
*/
if(obj.action !== 'returndirect' && obj.action !== 'reject'){
// 提交校验
let flag = await this.submitVerifyForm();
// 对比两条数据,dataType=2 的可编辑数据和前1条 月份填报数据不一致提示出来
if(!flag){
// 填报数据不一致 走 退回
callback(1, { userList: [{}] });
DesktopManager.showAlert({
type: 'warning',
content: `数据有异议,退回修改`
});
return
}
//---校验通过流程
}
},
},
destroyed: function () {}
};