超级码吏 2025-07-22 09:07 采纳率: 27.1%
浏览 27

element-plus 表格动态列校验

有一个列是动态的,有时候是校验人员,有时候是校验账号。怎么实现动态字段校验?

img

怎么校验【付款账户/人员】列?这列分别是好几个字段,要分别校验

  • 写回答

6条回答 默认 最新

  • 檀越@新空间 2025-07-22 09:08
    关注

    上午好☀️☀️☀️️
    本答案参考通义千问

    在使用 Element Plusel-table 时,如果表格的列是动态变化的(比如某一列可能是“校验人员”,也可能是“校验账号”),并且该列包含多个字段(如“付款账户/人员”列中包含“账户名”、“账号”、“姓名”等子字段),那么需要实现动态字段校验


    ✅ 解决方案概述

    为了实现动态列的校验,我们需要:

    1. 动态定义表格列(根据业务逻辑切换显示的列);
    2. 为动态列绑定校验规则(使用 rules 属性);
    3. 对动态列中的多个字段进行逐个校验(例如“付款账户/人员”列中有多个子字段);
    4. 结合 el-formel-table 实现整体表单校验

    🧠 关键点说明

    • 使用 el-tablecolumns 动态生成;
    • 每个列可以配置 proplabelrules
    • 对于多字段的列(如“付款账户/人员”),可以将其拆分为多个子字段,并分别设置校验规则;
    • 最终通过 el-form 提供的 validate 方法进行整体校验。

    🔧 实现步骤

    1. 定义数据结构和校验规则

    data() {
      return {
        tableData: [
          {
            id: 1,
            // 根据列动态展示的内容
            name: '张三',
            account: 'ZS123456',
            personName: '张三',
            paymentAccount: 'P123456',
            paymentPerson: '李四'
          }
        ],
        columns: [], // 动态列
        rules: {
          name: [{ required: true, message: '请输入姓名', trigger: 'blur' }],
          account: [{ required: true, message: '请输入账号', trigger: 'blur' }],
          personName: [{ required: true, message: '请输入人员名称', trigger: 'blur' }],
          paymentAccount: [{ required: true, message: '请输入付款账户', trigger: 'blur' }],
          paymentPerson: [{ required: true, message: '请输入付款人员', trigger: 'blur' }]
        },
        formRef: null
      };
    }
    

    2. 动态生成列

    mounted() {
      this.generateColumns();
    }
    
    methods: {
      generateColumns() {
        const dynamicColumn = {
          label: '付款账户/人员',
          prop: 'paymentAccount',
          rules: this.rules.paymentAccount,
          render: (h, { row }) => {
            return h('div', [
              h('el-input', {
                props: { value: row.paymentAccount },
                on: {
                  input: (value) => {
                    row.paymentAccount = value;
                  }
                }
              }),
              h('el-input', {
                props: { value: row.paymentPerson },
                on: {
                  input: (value) => {
                    row.paymentPerson = value;
                  }
                }
              })
            ]);
          }
        };
    
        // 可以根据条件切换列
        if (this.isPaymentMode) {
          this.columns = [
            { label: '姓名', prop: 'name', rules: this.rules.name },
            { label: '账号', prop: 'account', rules: this.rules.account },
            dynamicColumn
          ];
        } else {
          this.columns = [
            { label: '姓名', prop: 'name', rules: this.rules.name },
            { label: '人员名称', prop: 'personName', rules: this.rules.personName }
          ];
        }
      }
    }
    

    注意: 如果你希望将“付款账户/人员”作为一个单元格内多个字段并行展示,可以通过 render 函数自定义渲染内容。


    3. 绑定 el-formel-table

    <template>
      <el-form ref="formRef" :model="tableData" :rules="rules">
        <el-table :data="tableData" border>
          <el-table-column
            v-for="(col, index) in columns"
            :key="index"
            :label="col.label"
            :prop="col.prop"
          >
            <template #default="scope">
              <!-- 如果有自定义渲染 -->
              <div v-if="col.render">
                {{ col.render(h, scope) }}
              </div>
              <!-- 否则默认渲染 -->
              <el-input
                v-model="scope.row[col.prop]"
                @input="onInput(scope.row, col.prop)"
              />
            </template>
          </el-table-column>
        </el-table>
    
        <el-button @click="submitForm">提交</el-button>
      </el-form>
    </template>
    

    4. 提交表单并校验

    methods: {
      submitForm() {
        this.$refs.formRef.validate((valid) => {
          if (valid) {
            alert('校验通过');
          } else {
            alert('校验失败');
            return false;
          }
        });
      }
    }
    

    ⚠️ 注意事项

    • 动态列的 prop 必须与 tableData 中的字段对应
    • rules 中的字段必须与 prop 匹配
    • 对于多字段的列(如“付款账户/人员”),建议拆分成多个字段,并在 rules 中分别设置;
    • 使用 render 函数时,注意事件绑定和数据更新

    ✅ 总结

    | 步骤 | 内容 | |------|------| | 1 | 定义动态列和对应的校验规则 | | 2 | 使用 render 自定义复杂列的渲染 | | 3 | 将 el-tableel-form 结合使用 | | 4 | 调用 formRef.validate() 进行整体校验 |


    💡 示例代码(完整 Vue 组件)

    <template>
      <el-form ref="formRef" :model="tableData" :rules="rules">
        <el-table :data="tableData" border>
          <el-table-column
            v-for="(col, index) in columns"
            :key="index"
            :label="col.label"
            :prop="col.prop"
          >
            <template #default="scope">
              <el-input
                v-if="!col.render"
                v-model="scope.row[col.prop]"
                @input="onInput(scope.row, col.prop)"
              />
              <div v-else>
                {{ col.render(h, scope) }}
              </div>
            </template>
          </el-table-column>
        </el-table>
    
        <el-button @click="submitForm">提交</el-button>
      </el-form>
    </template>
    
    <script>
    export default {
      data() {
        return {
          tableData: [
            {
              id: 1,
              name: '',
              account: '',
              personName: '',
              paymentAccount: '',
              paymentPerson: ''
            }
          ],
          columns: [],
          rules: {
            name: [{ required: true, message: '请输入姓名', trigger: 'blur' }],
            account: [{ required: true, message: '请输入账号', trigger: 'blur' }],
            personName: [{ required: true, message: '请输入人员名称', trigger: 'blur' }],
            paymentAccount: [{ required: true, message: '请输入付款账户', trigger: 'blur' }],
            paymentPerson: [{ required: true, message: '请输入付款人员', trigger: 'blur' }]
          },
          isPaymentMode: true,
          formRef: null
        };
      },
      mounted() {
        this.generateColumns();
      },
      methods: {
        generateColumns() {
          const dynamicColumn = {
            label: '付款账户/人员',
            prop: 'paymentAccount',
            rules: this.rules.paymentAccount,
            render: (h, { row }) => {
              return h('div', [
                h('el-input', {
                  props: { value: row.paymentAccount },
                  on: {
                    input: (value) => {
                      row.paymentAccount = value;
                    }
                  }
                }),
                h('el-input', {
                  props: { value: row.paymentPerson },
                  on: {
                    input: (value) => {
                      row.paymentPerson = value;
                    }
                  }
                })
              ]);
            }
          };
    
          if (this.isPaymentMode) {
            this.columns = [
              { label: '姓名', prop: 'name', rules: this.rules.name },
              { label: '账号', prop: 'account', rules: this.rules.account },
              dynamicColumn
            ];
          } else {
            this.columns = [
              { label: '姓名', prop: 'name', rules: this.rules.name },
              { label: '人员名称', prop: 'personName', rules: this.rules.personName }
            ];
          }
        },
        submitForm() {
          this.$refs.formRef.validate((valid) => {
            if (valid) {
              alert('校验通过');
            } else {
              alert('校验失败');
              return false;
            }
          });
        }
      }
    };
    </script>
    

    如果你还有更复杂的场景(如多层级嵌套字段、动态列数量等),也可以继续扩展这个方案。欢迎继续提问!

    评论

报告相同问题?

问题事件

  • 创建了问题 7月22日