vue/element表格配置化

配置化想法萌生

表格配置化主要能解决的问题就是 提高代码复用能力、提升开发效率,特别是需要开发多个大型表单系统的,配置化可以极大的提升效率,让你上班摸鱼不再是梦想!为了早点下班,我们接着往下看吧!

配置化思路其实就是对表单项进行了抽象,制定了一份协议去描述每个表单项,具体对象中的每个属性有什么用。

用配置化方式开发表单,完完全全就是为了高复用、可维护性,然后提升开发效率,解放生产力。

  1. 高复用:相似的业务逻辑进行统一处理,复用在相似领域的业务场景。如果说投放系统只需要接入一个渠道,那真的写 template 一把梭就完了。但事实上却不是这样的,当你接入了第一个 facebook ,你发现后面还有 tiktok巨量引擎广点通 等各种媒体渠道…
  2. 可维护:实现配置代替开发。即使把配置抽离,交到非技术人员处,其根据协议一样能实现表单项的增删,完成业务。并不是把东西做出来就完事了。首先,渠道方会有新配置功能推出,这个是不可控的。其次,系统开发时并不是全字段接入,而是先接入业务方所需要的核心配置,所以后期会有很多接入新的字段需求。

设计协议

首先我们思考下我们的每个表单项目需要一些什么:

  1. type 类型。比如 inputselectradio 等等
  2. label 表单项的名称/描述
  3. formKey 字段名。我们提交数据到后段的字段名,比如 form.name'name'
  4. value 存放表单值。表单上 v-model 所绑定的值
  5. options 配置项。比如配置 multipledisabled是否显示 等等

举例如下:

config.js

export default [
  {
    type: 'el-input',
    label: '活动名称',
    formKey: 'name',
    value: '', // 默认值为空字符串
    options: {
      vIf: [
        // 表示:当 form.area === 'area1',才显示
        { relationKey: 'area', value: 'area1' }
      ]
    }
  },
  {
    type: 'el-select',
    label: '活动区域',
    formKey: 'area',
    value: 'area1',
    options: {
      multiple: true
    },
    optionData: [ // 这里模拟去后端拉回数据
      { label: '区域1', value: 'area1' },
      { label: '区域2', value: 'area2' }
    ]
  }
]

render函数

FormItemDemo.vue

<script>
export default {
  name: "FormItemDemo",
  props: {
    itemConfig: Object // 接收配置,外部传入
  },
  computed: {
  componentShow () {
    const vIfArr = this.itemConfig?.options.vIf
    if (!vIfArr) return true
    const relationArr = this.config.filter(config => vIfArr.find(vIf => vIf.relationKey === config.formKey))
    for (const relationItem of relationArr) {
      const vIfItem = vIfArr.find(_ => _.relationKey === relationItem.formKey)
      // 这里就是判断 联动的表单值 是否不满足 可以显示 的条件,不满足则不显示
      if (relationItem.value !== vIfItem.value) return false
    }
    return true
  }
},
  render(createElement) {
  //render 执行时判断是否展示,不展示的话返回空即可
  if(this.componentShow) return
    return createElement('el-form-item', {
      props: {
        label: this.itemConfig.label // 表单项的label
      }
    }, [
        // 表单组件
        createElement(this.itemConfig.type, {
          props: {
            value: this.itemConfig.value // 这里是自己实现一个 v-model
          },
          on: {
            change: (nVal) => { // 这里是自己实现一个 v-model
              this.itemConfig.value = nVal
            }
          }
        }, this.itemConfig.optionData && this.itemConfig.optionData.map(option => {
          // 这里只是 本demo 处理 el-select 的 option 数据,实际大家根据具体业务来实现即可
          return createElement('el-option', { props: { label: option.label, value: option.value } })
        }))
    ])
  }
}
</script>

custom.vue

<template>
  <div>
    <el-form label-width="100px">
      <FormItemDemo v-for="item in config" :item-config="item" />
    </el-form>
  </div>
</template>

<script>
import FormItemDemo from "./components/FormItemDemo.vue";
import config from "./config";

export default {
  name: 'App',
  components: { FormItemDemo },
  data () {
    return {
      config
    }
  }
}
</script>

优化函数

采用这种方式对我们的 config 进行 非响应式 优化。其实整个 config 数据,我们只是需要保证 value 是响应式的即可,其他很多描述性数据都是大可不必的。那我们就把其他字段进行一个优化~

function optimize (array) {
  return array.reduce((acc, cur) => {
    for (const key of Object.keys(cur)) {
      if (key === 'value') continue
      // 将不是 value 的属性都进行非响应式优化
      Object.defineProperty(cur, [key], { enumerable: false })
    }
    acc.push(cur)
    return acc
  }, [])
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值