文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

vue如何封装一个高质量的表单通用组件

2023-07-05 11:09

关注

这篇“vue如何封装一个高质量的表单通用组件”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“vue如何封装一个高质量的表单通用组件”文章吧。

基于Element-plus实现二次封装表单组件

封装一个高质量的通用组件,上面是真的只是基操,话不多说,直接上实践手把手教你封装组件。

步骤1

继承原有组件的所有特性(这也是封装的核心)。先明确三个大方向:

表单固定属性,继承Form表单的所有属性、方法。

 // 定义el-form的ref继承原有组件的form属性 export interface FormInstance {  registerLabelWidth(width: number, oldWidth: number): void,  deregisterLabelWidth(width: number): void,  autoLabelWidth: string | undefined,  emit: (evt: string, ...args: any[]) => void,  labelSuffix: string,  inline?: boolean,  model?: Record<string, unknown>,  size?: string,  showMessage?: boolean,  labelPosition?: string,  labelWidth?: string,  rules?: Record<string, unknown>,  statusIcon?: boolean,  hideRequiredAsterisk?: boolean,  disabled?: boolean,  validate: (callback?: Callback) => Promise<boolean>,  resetFields: () => void,  clearValidate: (props?: string | string[]) => void,  validateField: (props: string | string[], cb: ValidateFieldCallback) => void,}

表单项固定属性,继承表单项的所有属性、方法。

// 表单每一项的配置选项export interface FormOptions {  // 表单项显示的元素  type: '',// 定义表单项类型  value?: any, // 表单项的值  label?: string,// 表单项label  prop?: string,// 表单项的标识  rules?: RuleItem[],// 表单项的验证规则  placeholder?: string,// 表单项的占位符  attrs?: {  // 按需定义不同表单类型属性    ...  },  children?: FormOptions[],// 表单项的子元素,可能存在嵌套表单组件,如select  ....// 适当扩展我们需要的属性,比如上传组件属性,行布局表单属性}

由于Element-plus组件都是以el-为前缀,所以type取值只需要取el-后面部分作为值就行,比如el-input取 'input' 为值。

vue如何封装一个高质量的表单通用组件

表单验证效果,继承组件原有的所有验证属性。由于Element-plus的验证都是使用 async-validator 这个插件的验证方法,直接复用插件源码路径async-validator/src/interface.ts文件下的所有代码:

// 核心代码:封装验证方式时的属性export interface RuleItem {  type?: RuleType; // 验证种类  required?: boolean;// 是否必填  pattern?: RegExp | string;// 验证方式匹配  min?: number; // 表单项最小值  max?: number; // 表单项最大值  len?: number; // 表单项字符长度  trigger?: string | string[];// 验证触发方式  ....}

步骤2

实现一个完善的通用组件封装,通过对标签封装、接口 暴露、开发者传参等。明确表单类型,根据不同类型表单复用多种场景,不仅开发者用户拓展,而且,让开发者用最少代码就可以复用:

<!--表单框架:model就是传入的表单对象,rules就是传入的验证对象 -->  <el-form    v-if="model"    :validate-on-rule-change="false"    v-bind="$attrs"    :model="model"    :rules="rules"    ref="form"  >    ... <!--表单项封装 -->  </el-form>

普通表单项封装,比如日期、输入等组件。

<template v-for="(item, index) in options" :key="index">    <el-form-item  :label="item.label" :prop="item.prop">      <component        v-else        :is="`el-${item.type}`"        v-bind="item.attrs"        v-model="model[item?.prop!]"      >      </component>    </el-form-item></template>

嵌套表单项封装,比如下拉框,除了select组件还嵌套option组件。

<template v-for="(item, index) in options" :key="index">    <el-form-item      v-if="item.children && item.children.length"      :label="item.label"      :prop="item.prop"    >      <component        :is="`el-${item.type}`"        v-bind="item.attrs"        v-model="model[item?.prop!]"      >        <component          v-for="(child, i) in item.children"          :key="i"          :label="child.label"          :value="child.value"          :is="`el-${child.type}`"        >        </component>      </component>    </el-form-item></template>
富文本表单项封装

本文使用的是wangEditor。

<div id="editor" v-else-if="item.type === 'editor'"></div>
import E from 'wangeditor';// 遍历传入的prop的options对象,初始化富文本if (item.type === 'editor') {// 初始化富文本nextTick(() => {  if (document.getElementById('editor')) {    const editor = new E('#editor');    editor.config.placeholder = item.placeholder!;    editor.create();    // 初始化富文本的内容    editor.txt.html(item.value);    editor.config.onchange = (newHtml: string) => {      model.value[item.prop!] = newHtml;    };    edit.value = editor;  }});}
上传表单项封装

向开发者暴露上传的核心方法:预览、删除、上传成功等,同时允许开发者自定义上传信息以及渲染区域等。

<el-form-item  :label="item.label" :prop="item.prop">  <!-- 上传表单 -->  <el-upload    v-if="item.type === 'upload'"    v-bind="item.uploadAttrs"    :on-preview="onPreview"    :on-remove="onRemove"    :on-success="onSuccess"    :on-error="onError"    :on-progress="onProgress"    :on-change="onChange"    :before-upload="beforeUpload"    :before-remove="beforeRemove"    :http-request="httpRequest"  >    <slot name="uploadArea"></slot>    <slot name="uploadTip"></slot>  </el-upload></el-form-item>
同行多个表单布局封装

有时业务需要,一行可以定义多个表单,所以需要使用el-row,此时需要修改FormOptions属性接口,完善多个表单场景,cols是一个数组定义FormOptions数组,colOption是el-col组件的相关属性,然后重新复用嵌套表单的代码。

<template v-if="item.type === 'row'">    <el-row :gutter="item.rowGutter">    <el-col    v-for="(jtem, jndex) in item.cols"    v-bind="jtem.colOption"    :key="jndex"    >    <el-form-item :label="jtem.label" :prop="jtem.prop">      <component        :is="`el-${jtem.type}`"        v-bind="jtem.attrs"        v-model="model[jtem?.prop!]"      >        <template v-if="jtem.children && jtem.children.length">          <component            v-for="(child, i) in jtem.children"            :key="i"            :label="child.label"            :value="child.value"            :is="`el-${child.type}`"          >          </component>        </template>      </component>    </el-form-item>    </el-col>    </el-row></template>

提交取消按钮区域:这个最好可以实现插槽让开发者可以自定义。

<el-form-item>      <slot name="action" :form="form" :model="model"></slot></el-form-item>

步骤3

开发者的调用封装组件,通过配置不同表单类型的数组,然后调用lib-form封装组件实现业务代码复用。

组件的调用:根据业务需要,可以适当定义我们需要的组件属性以及必须要传的参数。

<lib-form  ref="form"  label-width="100px"  :options="options"  @on-change="handleChange"  @before-upload="handleBeforeUpload"  @on-preview="handlePreview"  @on-remove="handleRemove"  @before-remove="beforeRemove"  @on-success="handleSuccess"  @on-exceed="handleExceed">  <template #uploadArea>    <el-button size="small" type="primary">Click to upload</el-button>  </template>  <template #uploadTip>    <div >      jpg/png files with a size less than 500kb    </div>  </template>  <template #action="scope">    <el-button type="primary" @click="submitForm(scope)">提交</el-button>    <el-button @click="resetForm">重置</el-button>  </template></lib-form>

表单项的配置数组:由于这配置数组比较长,所以一般可以单独抽离出来,不要写在vue文件中,这样可以提高代码的可读性。

// 这里以多行表单布局为例子let options: FormOptions[] = [  {    type: 'row',    rowGutter: 20,    cols: [      {        type: 'input',        value: '',        label: '用户名',        prop: 'username',        placeholder: '请输入用户名',        rules: [          {            required: true,            message: '用户名不能为空',            trigger: 'blur',          },          {            min: 2,            max: 6,            message: '用户名在2-6位之间',            trigger: 'blur',          },        ],        attrs: {          clearable: true,        },        colOption: {          offset: 0,          span: 12,        },      },      {        type: 'input',        value: '',        label: '用户名',        prop: 'username',        placeholder: '请输入用户名',        rules: [          {            required: true,            message: '用户名不能为空',            trigger: 'blur',          },          {            min: 2,            max: 6,            message: '用户名在2-6位之间',            trigger: 'blur',          },        ],        attrs: {          clearable: true,        },        colOption: {          offset: 0,          span: 12,        },      },    ],  }, ]

以上就是关于“vue如何封装一个高质量的表单通用组件”这篇文章的内容,相信大家都有了一定的了解,希望小编分享的内容对大家有帮助,若想了解更多相关的知识内容,请关注编程网行业资讯频道。

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯