Vue + Element 实现动态表单

1. 需求:点击发送按钮新增一个表单并校验,校验通过调用后端接口,发送按钮禁用

优化:因为需求规定一个页面只需要出现三个question和answer表单就可以,所以可以设置重置按钮优化只能发送三条question的问题

应该存在更简单的写法,但我cai,嘿嘿嘿

表单初始状态

点击发送按钮,新增一条表单

2. 踩的坑

(1)去年用表格做过相似需求,但表格会有一些特有的奇怪东西,所以选择使用form表单

(2)关于表单校验问题,在data里写表单校验的规则时,会出现无法校验的情况,所以直接绑给了标签

(3)最开始使用普通数组计数循环实现表单的动态新增,el-form-item的值绑定的是question[index]类似的值,但效果不对,会出现很多奇怪的bug,所以选择循环form.formArr,问题表单绑定值为item.question

3. 页面布局

<div class="container" v-loading="loading">
  <div class="content" v-for="(item, index) in form.formArr" :key="item.key">
    <div class="top-content" >
      <div class="question">
        <el-form :model="form" :rules="rules" ref="queryForm" label-width="70px">
          <el-form-item label="问题:" 
            :prop="'formArr.' + index + '.question'"
            :rules="{ required: true, message: '问题不能为空', trigger: 'blur' }">
            <el-input
              type="textarea"
              clearable
              size="medium"
              :rows="2"
              :autosize="{ minRows: 2}"
              placeholder="请输入问题..."
              v-model="item.question">
            </el-input>
          </el-form-item>
        </el-form>
        <div class="button">
          <el-button :disabled="item.disabled" @click="sendHandle('queryForm', index)">发送</el-button>
        </div>
      </div>
      <div class="answer">
        <div class="label">回答:</div>
        <el-input 
          v-model="item.answer" 
          type="textarea" 
          size="medium" 
          :rows="2" 
          :autosize="{ minRows: 2}"
          readonly>
        </el-input>
      </div>
    </div>
  </div>
</div>

4. data部分

data() {
    return {
      form: {
        formArr: [
          {
            question: "",
            answer: "",
            disabled: false
          }
        ]
      },
      answer: [],
      loading: false,
    }
  },

5. 函数部分

sendHandle(formName, index) {
      this.$refs[formName][index].validate((valid) => {
          if (valid) {
            this.loading = true;
            let form = {
              question: this.form.formArr[index].question
            }
            getAnswer(form)
              .then(res => {
                if(res.code == 200) {
                  for(var i = 0; i < res.result.length; i++) {
                    if(res.result[i].role == 'assistant'){
                      this.form.formArr[index].answer = res.result[i].content;
                    }
                  }
                    // 需求规定:最多三条表单(可以添加重置按钮进行需求优化)
                  if(this.form.formArr.length < 3) {
                    this.form.formArr.push({
                      question: '',
                      answer: '',
                      disabled: false
                    });
                  }
                  this.loading = false;
                  this.form.formArr[index].disabled = true;
                  this.$message({
                    type: 'success',
                    message: '发送成功'
                  })
                }
              })
              .catch(err => {
                console.log(err);
              })

          } else {
            return false;
          }
        });
    },

总结一下吧,希望不要再踩这个坑了

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值