iView复合型输入框动态生成表达式

发布于:2023-01-08 ⋅ 阅读:(625) ⋅ 点赞:(0)

一,需求分析

需求: 实现一个预警功能,需要动态配置一些参数,前端需要根据下拉选中类型实现动态添加表达式的功能;

二,功能实现

1.常用的复合型输入框

在这里插入图片描述
官网参考:input输入框

2.项目功能中需要一个可以编辑修改,下拉动态生成的表达式显示配置。

改装后的样子

在这里插入图片描述
可以添加多个配置名称的样子

在这里插入图片描述
以及实现表达式的查看,修改功能。下面简单介绍下实现过程:

a.新增时选择类型下拉,根据所选中的类型,动态生成表达式的名称和参数:

在这里插入图片描述

新增时如何动态生成表达式?

    //新增确认
    addSignConfig() {
      this.editTitle = "新增";
      this.addParamsList=[];
      this.changeApp();  //动态选中触发方法
      this.$refs.editForm.resetFields();
      this.showButton = true;
      this.signShow = true;
       this.getAllwarnType();//类型下拉接口
    },

类型下拉:

          <FormItem prop="warnTypeId" label="预警类型名称">
            <Select
              v-model="editForm.warnTypeId"
              clearable
              filterable
              class="search-input"
              @on-change="changeApp(editForm.warnTypeId)"
              :disabled="this.editTitle == '查看'||this.editTitle == '修改预警规则'" >
              <Option
                v-for="(item, index) in warnTypeList"
                :key="`state-${index}`"
                :value="item.code"
                >{{ item.name }}</Option
              >
            </Select>
          </FormItem>

b.动态生成新增时的表达式:

  <FormItem label="表达式配置新增" prop="setExpression" 
               :maxlength="100" v-if="this.editTitle == '新增预警规则'&&this.addParamsList!=null">
          <Input v-model="item.val" style="width: 320px"  ref="setVal"
                 v-for="(item, index) in addParamsList"  :key="`state-${index}`"
                   @on-blur="handleAddChange(index, item)">
            <Select v-model="item.attrName" slot="prepend" style="width: 140px" disabled>
                 <Option :value="item.attrName">{{ item.attrName }}</Option >
            </Select>
            <Button slot="append" class='add' v-if="item.attrType==0" style="width: 72px">%</Button>
            <Button slot="append" class='add' v-if="item.attrType==1" style="width: 72px">Number</Button>
            <Button slot="append" class='add' v-if="item.attrType==2&&index!==1" style="width: 72px">String</Button> 
            <div slot="append" class='add' v-if="item.attrName=='失败代码'&&index===1" style="width: 58px;background-color:white">
            <Icon v-if="item.attrName=='失败代码'&&index===1" custom="iconfont icon-jiahaoyou-lanx" size="22" color="#5173FF" @click="add()"></Icon>
            <Icon v-if="item.attrName=='失败代码'&&index===1" custom="iconfont icon-jianshao" size="18" color="#5173FF" @click="del(index,item)"></Icon>
            </div>
         </Input>
      </FormItem>

c.类型下拉接口的范例数据

params: "[{\"attr\":\"successRate\",\"attrName\":\"成功率低于\",\"attrTpe\":0}]"

d.选中类型时的方法

.map获取所需属性到新数组

    changeApp(warnTypeId) {
      if (warnTypeId == undefined) {
        this.addParamsList=null;
        return;
      } else {
        var fun = this.warnTypeList.filter(function (c, i, a) {
          if (c.code == warnTypeId) {
            return c.params;
          }
        });
        this.downParamsList = JSON.parse(fun[0].params);
        let setParamsList =this.downParamsList.map(item => {
          return {
            attr: item.attr,
            attrName: item.attrName,
            attrType:item.attrTpe,
            val: "",
          };
        });
    //失败代码顺序调换
     if(setParamsList){
       this.changeIndex(setParamsList);
      }
       this.addParamsList= setParamsList;
      }
    },

addParamsList:[]
根据 this.addParamsList生成表达式名称和表达式参数;

如此,就可以根据类型接口动态生成出表达式名称和输入框

在这里插入图片描述

e.接下来,输入数据,如何获取并保存数据呢?

使用@on-blur获取数据:

     handleAddChange(index, item){
        if(!this.$refs.setVal[index].value){
           this.editForm.expression=""
        }
        if(this.$refs.setVal[index].value){
           this.editForm.expression=JSON.stringify(this.addParamsList);
        }
   }        

this.$refs.setVal[index].value获取输入框填入的值。

填写完数据后,可通过方法获取到实时填写的数据。这样就可以将新增的数据保存。

f.修改和查看与此功能比较类似,不过不用动态获取表达式配置参数和名称,直接从接口中获取
格式化处理取值即可。

获取参数样例:

expression: "[{\"attr\":\"count\",\"attrName\":\"次数\",\"attrType\":1,\"val\":\"1\"}]"

JSON.parse处理后显示:

修改:

  // 获取:
  if(this.editForm.expression){
                      //  this.updateParamsList = JSON.parse(this.editForm.expression);                      
                      let  getParamsList = JSON.parse(this.editForm.expression);
                          if(getParamsList){
                            this.changeIndex(getParamsList);
                          }
                         this.updateParamsList =getParamsList;
    }

显示:

       <FormItem label="表达式配置修改" prop="setExpression" 
               :maxlength="100" v-if="this.editTitle == '修改预警规则'&&this.updateParamsList.length>0">
          <Input v-model="item.val" style="width: 320px"  ref="setVal"
                 v-for="(item, index) in updateParamsList"  :key="`state-${index}`"
                   @on-blur="handleUpdateChange(index,item)">
            <Select v-model="item.attrName" slot="prepend" style="width: 140px" disabled>
                 <Option :value="item.attrName">{{ item.attrName }}</Option >
            </Select>
            <Button slot="append" class='add' v-if="item.attrType==0" style="width: 72px">%</Button>
            <Button slot="append" class='add' v-if="item.attrType==1" style="width: 72px">Number</Button>
            <Button slot="append" class='add' v-if="item.attrType==2&&index!==1" style="width: 72px">String</Button>
            <div slot="append" class='add' v-if="item.attrName=='失败代码'&&index===1" style="width: 58px;background-color:white">
            <Icon v-if="item.attrName=='失败代码'&&index===1" custom="iconfont icon-jiahaoyou-lanx" size="22" color="#5173FF" @click="adds()"></Icon>
            <Icon v-if="item.attrName=='失败代码'&&index===1" custom="iconfont icon-jianshao" size="18" color="#5173FF" @click="dels(index,item)"></Icon>
            </div>
         </Input>
      </FormItem>

保存: this.editForm.expression

JSON.stringify转换后保存

     handleUpdateChange(index, item){
      
       if(!this.$refs.setVal[index].value){
           this.editForm.expression=""
       }
      if(this.$refs.setVal[index].value){
            this.editForm.expression=JSON.stringify(this.updateParamsList);
       }
 }       

这样,就可以实现表达式的修改保存

修改样例传参:

expression: "[{\"attr\":\"count\",\"attrName\":\"次数\",\"attrType\":1,\"val\":\"1\"}]"

在这里插入图片描述
查看的方法比较类似,直接将输入框禁用掉即可

3.校验表达式输入:顺序,重复,类型及动态添加删除

a,校验顺序

配置多个名称时,将失败代码次数放到顶部,便于查看。

    changeIndex(failList){
      if(failList&&failList[0].attrName=="失败代码"){
        let  tempFirst  = failList[0];
        let  tempSecond = failList[1];
        failList[0] = tempSecond;
        failList[1] = tempFirst;
      }
       return failList
    },

b,配置多个失败代码的重复校验

new Set去重比较长度判断是否重复
.filter剔除多余的undefined值

          let arr=this.addParamsList.map(item =>{
              if(item.attrType==2||item.attrType==3){
                  return item.val;
              }
          }).filter(iten => iten!=undefined);
          let cutRepeat = Array.from(new Set(arr));
          if (cutRepeat.length < arr.length) {
            this.$Message.error('失败代码不能重复')
                return
          }

c,其它类型范围校验

.some非空校验

 if (this.updateParamsList.some((item) => item.val=== "")) {
            this.$Message.error('表达式配置参数不能为空!!!');
              return;
 }

其它类型校验

表达式:
非数字 isNaN
次数或特殊字段检测 search

正整数正则: !(/(^[1-9]\d*$)/.test(item.val))
       //表达式校验
          if (this.updateParamsList.some((item) => item.attrType===0&&isNaN(item.val)===true)){ 
              this.$Message.error('表达式配置参数百分比必须为数字!!!');
                return;
          }
          if (this.updateParamsList.some((item) => item.attrType===0&&item.val<0)) {
              this.$Message.error('表达式配置参数百分比范围为0~100 !!!');
                return;
          }
          if (this.updateParamsList.some((item) => item.attrType===0&&item.val>100)) {
              this.$Message.error('表达式配置参数百分比范围为0~100 !!!');
                return;
          }
          //次数校验
          if (this.updateParamsList.some((item) =>(item.attrType===1&&item.attrName.search("次数")!=-1)&&!(/(^[1-9]\d*$)/.test(item.val))) ) {
                this.$Message.error('表达式配置参数次数必须为正整数!!!');
                return;
          }
          //余额校验 
          if (this.updateParamsList.some((item) => item.attrType===1&&item.attrName=="余额小于"&&isNaN(item.val)===true)){ 
              this.$Message.error('表达式配置参数余额必须为数字!!!');
                return;
          }
          if (this.updateParamsList.some((item) => item.attrType===1&&item.attrName=="余额小于"&& item.val<-10)) { 
              this.$Message.error('表达式配置参数余额负数最大为-10!!!');
                return;
          }
          //失败代码校验
          if (this.updateParamsList.some((item) =>  item.attrType===2)&&this.updateParamsList.length>21) { 
              this.$Message.error('表达式配置参数失败代码最大为20条!!!');
                return;
          }

d.新增多个失败代码时新增,删除的方法
新增

 add(){
       if (this.addParamsList[0].attrName=="失败代码"&&this.addParamsList[0].val=="") {
              this.$Message.warning('请先填写前一个失败代码')
                return
        }
      //失败代码条数校验  
      if (this.addParamsList.length>20) {
              this.$Message.warning('失败代码最多添加20个')
                return
      }
      //失败代码重复校验
      let arr=this.addParamsList.map(item =>{
          if(item.attrType==2||item.attrType==3){
               return item.val;
          }
       }).filter(iten => iten!=undefined);
      let cutRepeat = Array.from(new Set(arr));
      if (cutRepeat.length < arr.length) {
        this.$Message.warning('失败代码重复或存在多个空值')
            return
      }
    
       let obj = this.addParamsList[this.addParamsList.length-1]
       if (!obj.val&&obj.attrName=="失败代码") {
             this.$Message.warning('请先填写前一个失败代码')
       }else{
             this.addParamsList.push({
             attr:"code",
             attrName:"失败代码",
             val:"",
             attrType:"2"
            })
        }
     },

删除

      del(index,item){
            if(this.addParamsList.length ===2){
                this.$Message.warning('至少有一个失败代码,不可删除!!')
                        return
            }if(this.addParamsList.length >2){
                 this.addParamsList.splice(this.addParamsList.length-1, 1)
            }
            this.handleAddChange(index, item);
     },

这样就用复合型input实现了动态生成表达式,修改查看,动态添加删除校验功能!!!。

在这里插入图片描述

此文仅input功能小小使用,简单总结,便于交流学习改进,喜欢就多点点关注评论,一起学习进步。

本文含有隐藏内容,请 开通VIP 后查看

网站公告

今日签到

点亮在社区的每一天
去签到