You need to enable JavaScript to run this app. Vue中如何复用@focus、@blur方法及多正则表单校验规则
优惠活动
大模型
产品
解决方案
定价
更多

Vue中如何复用@focus、@blur方法及多正则表单校验规则

Vue中focus/blur校验方法复用解决方案

针对第一个问题:根据fieldName判断当前触发字段的修复

原有代码存在两个核心问题:

  • blur方法中邮箱校验逻辑执行完成后直接return,导致后续姓名校验逻辑永远无法触发
  • focus和blur方法都硬编码了所有字段的错误状态操作,完全没有用到传入的fieldName参数

修复思路:利用JS对象的动态属性名特性,通过传入的字段名拼接出对应错误状态、错误提示、绑定值的属性名,仅操作当前触发事件的字段对应属性,不影响其他字段的状态。

针对第二个问题:多正则校验规则的复用方案

将所有字段的校验规则、错误提示抽成统一的配置映射表,无需为每个字段单独编写校验函数,新增校验字段仅需在映射表中新增对应配置即可,完全复用focus、blur逻辑。


修改后完整代码

JS逻辑

const app = new Vue({
  el: "#app",
  data: {
    // 补充v-model绑定的字段变量
    carrierEmail: '',
    carrierName: '',
    carrierEmailError: false,
    carrierNameError: false,
    carrierEmailErrMsg: '',
    carrierNameErrMsg: '',
  },
  methods: {
    // 校验规则配置中心,新增校验字段直接在此处加配置即可
    getValidatorMap() {
      return {
        carrierEmail: {
          rule: /^\w+((-\w+)|(\.\w+))*\@[A-Za-z0-9]+((\.|-)[A-Za-z0-9]+)*\.[A-Za-z]+$/,
          errMsg: '邮箱格式不正确'
        },
        carrierName: {
          rule: /^[A-Za-z0-9]{1,10}$/,
          errMsg: '姓名只能为1-10位字母或数字组合'
        }
      }
    },
    focus(fieldName) {
      // 仅清空当前触发字段的错误状态
      this[`${fieldName}Error`] = false
      this[`${fieldName}ErrMsg`] = ''
    },
    blur(fieldName) {
      const validator = this.getValidatorMap()[fieldName]
      // 无对应校验规则直接返回
      if (!validator) return
      // 校验当前字段值
      const isPass = validator.rule.test(this[fieldName])
      if (isPass) {
        this[`${fieldName}Error`] = false
        this[`${fieldName}ErrMsg`] = ''
      } else {
        this[`${fieldName}Error`] = true
        this[`${fieldName}ErrMsg`] = validator.errMsg
      }
    },
    // 补充原代码缺失的清空字段方法
    clearField(fieldName) {
      this[fieldName] = ''
      this[`${fieldName}Error`] = false
      this[`${fieldName}ErrMsg`] = ''
    }
  }
})

HTML模板

<html>
<head>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
</head>
<body>
  <div id="app">
    <div class="form-control invoice-form" :class="{ 'is-invalid': carrierEmailError }">
      <input v-model="carrierEmail" @blur="blur('carrierEmail')" @focus="focus('carrierEmail')" type="text" placeholder="E-MAIL">
    </div>
    <div class="invalid-feedback" v-show="carrierEmailError">
      {{ carrierEmailErrMsg }}
    </div>
    <div class="form-control invoice-form" :class="{ 'is-invalid': carrierNameError }">
      <input v-model="carrierName" @blur="blur('carrierName')" @focus="focus('carrierName')" type="text" placeholder="name">
      <div class="ic-clear" @click="clearField('carrierName')"></div>
    </div>
    <div class="invalid-feedback" v-show="carrierNameError">{{ carrierNameErrMsg }}</div>
  </div>
</body>
</html>

内容的提问来源于stack exchange,提问作者Chieh YU WU

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.17 06:24:04