Vue+Element动态表单校验

Vue+Element动态表单校验

最近项目中需要动态创建若干表单,并附加检验规则,踩了很多坑,在此写了一个小demo做一个记录

1. 效果展示

Vue+Element动态表单校验

2. 动态表单的创建(核心代码)

 <div v-for='(item, index) in dynamicFormData' :key='index'>
      <el-form  :model='item'   ref='dynamicForm' >
          <el-form-item prop = "channelName">    
           		<el-input v-model = "item.channelName" />
           </el-form-item>
       </el-form>
 </div>

3. 多个表单同时校验(核心代码)

	 let flag = 0
      for (let i = 0; i < this.passageway.count; i++) {
        try {
          let k = await this.$refs['dynamicForm'][i].validate()
          flag++
        } catch (e) {
          console.log('表单校验失败')
        }
      }
      // 根据flag === count来判断是否校验成功

4.完整代码

<template>
  <div>
    <h1>动态表单校验</h1>
    <el-row>
      <el-col :span='12'>
        <span>请选择通道数目</span>
        <el-select
          v-model='passageway.count'
          clearable
          placeholder='请选择通道数目'
          @change='changeCount'
          style='width: 220px; margin-left: 20px'
        >
          <el-option
            v-for='item in countArr'
            :label='item.label'
            :key='item.value'
            :value='item.value'
          />
        </el-select>
      </el-col>
    </el-row>

    <div v-for='(item, index) in dynamicFormData' :key='index'>
      <el-form
        :model='item'
        label-position='right'
        label-width='100px'
        ref='dynamicForm'
        size='small'
        :inline='true'
        label-suffix=':'
      >
        <div class='p-title'>通道{{ index + 1 }}</div>
        <!-- 第一行 -->
        <el-row>
          <el-col :span='8'>
            <el-form-item
              label='通道名称'
              prop='channelName'
              :rules="[
                    {
                      required: true,
                      message: '通道名称不能为空',
                      trigger: ['blur', 'change'],
                    },
                  ]"
            >
              <el-input
                type='text'
                v-model='item.channelName'
                style='width: 220px'
                clearable
                maxlength='50'
                placeholder='请输入通道名称'
              />
            </el-form-item>
          </el-col>
          <el-col :span='8'>
            <el-form-item label='设备类型' prop='terminalType' :rules="[
                    {
                      required: true,
                      message: '设备类型不能为空',
                      trigger: ['blur','change'],
                    },
                  ]">
              <el-select v-model='item.terminalType' placeholder='请选择设备类型' style='width: 220px' clearable>
                <el-option
                  v-for='item in deviceType'
                  :key='item.value'
                  :label='item.label'
                  :value='item.value'>
                </el-option>
              </el-select>
            </el-form-item>
          </el-col>
          <el-col :span='8'>
            <el-form-item label='摄像机种类' prop='vidiconSpecies'>
              <el-input
                type='text'
                v-model='item.vidiconSpecies'
                clearable
                maxlength='50'
                style='width: 220px'
                placeholder='请输入摄像机种类'
              />
            </el-form-item>
          </el-col>
        </el-row>

        <!-- 第二行 -->
        <el-row>
          <el-col :span='8'>
            <el-form-item label='型号' prop='model'>
              <el-input
                type='text'
                v-model='item.model'
                style='width: 220px'
                clearable
                maxlength='50'
                placeholder='请输入型号'
              />
            </el-form-item>
          </el-col>
          <el-col :span='8'>
            <el-form-item label='生产厂家' prop='productionFactory'>
              <el-input
                type='text'
                v-model='item.productionFactory'
                style='width: 220px'
                clearable
                maxlength='50'
                placeholder='请输入生产厂家'
              />
            </el-form-item>
          </el-col>
          <el-col :span='8'>
            <el-form-item label='安装地点' prop='installAddress'>
              <el-input
                type='text'
                v-model='item.installAddress'
                style='width: 220px'
                clearable
                maxlength='50'
                placeholder='请输入安装地点'
              />
            </el-form-item>
          </el-col>
        </el-row>

        <!-- 第三行 -->
        <el-row>
          <el-col :span='8'>
            <el-form-item label='使用状态' prop='usedState'>
              <el-radio v-model='item.usedState' label='1'>启用</el-radio>
              <el-radio v-model='item.usedState' label='0'>停用</el-radio>
            </el-form-item>
          </el-col>
          <el-col :span='8'>
            <el-form-item label='云台功能' prop='cloudPlatformFunction'>
              <el-radio v-model='item.cloudPlatformFunction' label='1'
              >启用
              </el-radio
              >
              <el-radio v-model='item.cloudPlatformFunction' label='0'
              >停用
              </el-radio
              >
            </el-form-item>
          </el-col>
          <el-col :span='8'>
            <el-form-item label='物理通道' prop='physicalChannel'>
              <el-input
                type='text'
                v-model='item.physicalChannel'
                style='width: 220px'
                clearable
                maxlength='50'
                placeholder='请输入终端型号'
              />
            </el-form-item>
          </el-col>
        </el-row>


      </el-form>
    </div>

    <el-button type='primary' @click='submitForm' v-if='passageway.count'>提交</el-button>
  </div>
</template>

<script>
export default {
  data() {
    return {
      passageway: {
        count: 1 // 默认通道数量
      },
      countArr: [], // 通道数量下拉框
      dynamicFormData: [],// 表单数组
      deviceType: [ // 设备类型
        { label: '车载视频设备', value: 1 },
        { label: '电动采集器', value: 2 },
        { label: '数据中心一体机', value: 3 }
      ]
    }
  },
  created() {
    this.initCount()
    this.initCountData()
  },
  methods: {

    // 通道数目变化
    changeCount(e) {
      this.passageway.count = e
      this.initCountData()
    },

    // 通道数目0-12
    initCount() {
      for (let i = 0; i <= 12; i++) {
        this.countArr.push({
          label: i,
          value: i
        })
      }
    },

    // 初始化通道表单数组
    initCountData() {
      this.dynamicFormData = []
      for (let i = 0; i < this.passageway.count; i++) {
        this.dynamicFormData.push({
          channelName: 'CH' + (i + 1),
          terminalType: undefined,
          vidiconSpecies: undefined,
          model: undefined,
          productionFactory: undefined,
          installAddress: undefined,
          usedState: '1',
          cloudPlatformFunction: '1',
          physicalChannel: undefined
        })
      }
    },

    // 校验表单
    async submitForm() {

      // 多个表单进行校验的标识
      let flag = 0
      for (let i = 0; i < this.passageway.count; i++) {
        try {
          let k = await this.$refs['dynamicForm'][i].validate()
          flag++
        } catch (e) {
          console.log('表单校验失败')
        }
      }

      if (flag !== this.passageway.count) {
        this.$message.error('表单校验失败')
      } else {
        this.$message.success('检验成功')
        console.log('表单要提交的数据:', JSON.parse(JSON.stringify(this.dynamicFormData)))
      }

    },

  }
}
</script>

<style scoped>
.p-title {
  font-size: 16px;
  font-weight: 700;
  width: 88%;
  height: 30px;
  line-height: 30px;
  background: #d9d9d9;
  margin: 3px auto 10px auto;
}
</style>```

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值