动态添加表单

 根据项目要求要动态添加表单并能传给后台,我采用的是ant design的 FormModel 表单,动态增减表单项(在最后一个例子),如下图:

 下面是我的实现图,主要功能有:

添加报表项(类型是 inputString,select),添加日期 类型是 date,添加地区 类型是 area,

删除报表项,添加报表项的子表单项,删除报表项的子表单项,上下移动整个报表项,输入报表项值

 看似简单的个动态添加表单项,实则工作量很大,下面上代码:

  <a-form-item
            v-for="(k,index) in reportItems"
            :key="index"
            :required="false"
          >
            <a-input
              @keyup="changeReportItemLabel(k.key)"
              v-decorator="[
                `names[${k.key}]`,
                {
                  validateTrigger: ['keyup', 'blur'],
                  initialValue:k.lable,
                  rules: [
                    {
                      required: true,
                      whitespace: true,
                      message: '请输入名称',
                    },
                  ],
                },
              ]"
              placeholder="请输入名称"
              style="width: 25%;
              border: none;
              border-bottom: 1px solid;
              border-radius: 0;"
            />
            <span style="margin:0 3px;">:</span>
            <a-input
              style="width: 60%; margin-right: 8px"
              :disabled="true"
            />
            <a-icon
              v-if="reportItems[index].type=='inputString'"
              type="plus-circle"
              theme="twoTone"
              twoToneColor="#52c41a"
              class="dynamic-delete-button"
              @click="addOne(index)"
            />
            <a-icon
              theme="twoTone"
              twoToneColor="red"
              type="minus-circle-o"
              class="dynamic-delete-button"
              @click="remove(index)"
            />
            <a-icon
              type="arrow-up"
              class="arrow"
              v-show="index == 0?false:true"
              @click="upFieldOrder(index)"
            />
            <a-icon
              type="arrow-down"
              class="arrow"
              v-show="index == reportItems.length - 1?false:true"
              :disabled="true"
              @click="downFieldOrder(index)"
            />
            <!--================================================================= -->
            <div
              style="margin-left: 25%"
            >
              <br>
              <a-form-item
                v-for="(item,idx) in k.options"
                :key="item.key"
                :required="false"
              >
                <span style="margin:0 3px;">:</span>
                <a-input
                  @keyup="ItemValue(k.key, item.key)"
                  v-decorator="[
                        `names[${k.key}]_options[${item.key}]`,
                          {
                          validateTrigger: ['keyup', 'blur'],
                          initialValue:item.val,
                          rules: [
                            {
                              required: true,
                              whitespace: true,
                              message: '请输入值',
                            }
                          ]
                      } 
                    ]"
                  style="width: 80%; margin-right: 8px"
                />
                <a-icon
                  class="dynamic-delete-button"
                  type="minus-circle-o"
                  @click="removeOne(index,idx)"
                />
              </a-form-item>
            </div>
          </a-form-item>
        </a-row>
        <a-row
          style="display: flex;justify-content: space-between;"
        >
          <a-form-item>
            <a-button
              type="dashed"
              style="width: 250px"
              @click="add('inputString')"
            >
              <a-icon type="plus" /> 添加报表项
            </a-button>
          </a-form-item>
          <a-form-item>
            <a-button
              type="dashed"
              style="width: 250px"
              @click="add('date')"
            >
              <a-icon type="plus" />日期
            </a-button>
          </a-form-item>
          <a-form-item>
            <!-- :disabled="reportItems.filter(e=>e.type=='area').length>=1?true:false" -->
            <a-button
              type="dashed"
              style="width: 250px"
              @click="add('area')"
            >
              <a-icon type="plus" />地区
            </a-button>
          </a-form-item>
export default {
  data () {
    return {
      diable: false,
      reportItems: [],//报告结构
      form: this.$form.createForm(this),
    }
  },
  methods: {
    //=============================动态构建报告项 begin================================

    changeReportItemLabel (k) {
      let lable = this.form.getFieldValue(`names[${k}]`)
      this.reportItems.filter(e => e.key == k)[0].lable = lable
    },
     /**
     * 删除一整个报表项
     */
    remove (k) {
      this.reportItems.splice(k, 1)
    },
    /**
     * 添加一整个报表项
     */
    add (type) {
      this.reportItems.push({ key: this.reportItems.length, type: type, options: [] })
    },
    /**
     * 移除一个报表项的子表单项
     */
    removeOne (k, k2) {
      this.reportItems[k].options.splice(k2, 1)
    },
   
    /**
     * 添加一个报表项的子表单项
     */
    addOne (oneIndex) {
      let reportItem = this.reportItems[oneIndex]
      let lastItem = reportItem.options[reportItem.options.length - 1]
      let key2 = lastItem ? lastItem.key + 1 : 0
      this.reportItems[oneIndex].options.push({ key: key2 })
    },

    /**
     * 报表项的子表单项---输入值并传给后台
     */
    ItemValue (key1, key2) {
      let value = this.form.getFieldValue(`names[${key1}]_options[${key2}]`)
      this.reportItems[key1].options[key2].val = value
    },
    /**
     * 上移
     */
    upFieldOrder (index) {
      let temp = this.reportItems[index - 1]
      Vue.set(this.reportItems, index - 1, this.reportItems[index])
      Vue.set(this.reportItems, index, temp)
      console.log('reportItems---------', this.reportItems)
    },
    /**
     * 下移
     */
    downFieldOrder (index) {
      let down = this.reportItems[index + 1]
      Vue.set(this.reportItems, index + 1, this.reportItems[index])
      Vue.set(this.reportItems, index, down)
      console.log('reportItems---------', this.reportItems)
    },
    //=============================动态 end==================================

    onSave () {
      this.form.validateFields((err, fieldsValue) => {
        let { code, title } = fieldsValue
       // 在此处判断element.options的类型是什么,默认是inputString,有子表单项时是select
        this.reportItems.forEach(element => {
          if (element.options.length > 0) {
            element.type = 'select'
          }
        })

        if (!err) {
              this.conditions.content = JSON.stringify(this.reportItems)
              projectItemsAdd(this.conditions).then(res => {
                this.onClose()
                this.$parent.getCategory()
              })
        }
      })
    }
  }
}

 

全是个人写项目所得,有什么不懂得可以欢迎评论提问

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值