表单验证提交时,验证不通过时,快速定位到未通过的表单元素(第一个未通过的元素)位置

941 阅读1分钟

当项目开发时,提交表单,验证未通过的表单元素在页面上只会在文字提示,那有什么方法可以快速定位到未通过校验的元素呢?是的,scrollIntoView()即可实现。scrollIntoView()方法将调用它的元素滚动到浏览器窗口的可见区域。 最终实现的效果:

跳转至未通过的item.gif 上代码: 在父组件引入各部分的表单组件,form1-form7,该demo只是个例子,因此form1到form7的代码一模一样,form1代码如下:

<template>
  <el-form :model="form" :rules="rules" ref="form">
    <el-form-item label="姓名" prop="name">
      <el-input v-model="form.name"></el-input>
    </el-form-item>
    <el-form-item label="年龄" prop="age">
      <el-input v-model="form.age"></el-input>
    </el-form-item>
    <el-form-item label="地址" prop="address">
      <el-input v-model="form.address"></el-input>
    </el-form-item>
  </el-form>
</template>

<script>
export default {
  data() {
    return {
      form: {
        name: '',
        age: '',
        address: ''
      },
      rules: {
        name: [
          {required: true, message: 'required', trigger: 'blur'}
        ],
        age: [
          {required: true, message: 'required', trigger: 'blur'}
        ],
        address: [
          {required: true, message: 'required', trigger: 'blur'}
        ]
      }
    }
  },
  methods: {
    validate() {
      return new Promise(resolve => {
        this.$refs.form.validate(async vaild => {
          if (!vaild) {
            await this.$nextTick()
            this.$scrollToError(this.$refs.form.$el)
          }
          resolve(vaild)
        })
      })
    }
  }
}
</script>

scrollToError方法是在utils文件夹下定义的方法

/**
 * 提交表单时,自动滚动到错误的校验框
 *
 * @param {*} el 包裹的元素
 * @param {string} [scrollOption={
 *     behavior: 'smooth',
 *     block: 'center'
 *   }] 滚动参数
 * @param {*} className 报错误的类名
 */
export const scrollToError = (
  el,
  scrollOption = { behavior: "smooth", block: "center" },
  className = 'is-error'
) => {
  const isError = el.getElementsByClassName(className)
  isError[0].scrollIntoView(scrollOption)
};

为方便使用,将scrollToError()方法挂载到vue原型上,在页面调用直接可this.$scrollToError()

// main.js页面

import { scrollToError } from '@/utils/dom.js'  // 引入

Vue.prototype.$scrollToError = scrollToError  // 挂载到原型上

然后在父组件使用,代码如下:

<template>
  <div class="box-container">
    <div style="padding: 10px">
      <el-card>
        <form1 ref="form1"></form1>
      </el-card>
      <el-card>
        <form2 ref="form2"></form2>
      </el-card>
      <el-card>
        <form3 ref="form3"></form3>
      </el-card>
      <el-card>
        <form4 ref="form4"></form4>
      </el-card>
      <el-card>
        <form5 ref="form5"></form5>
      </el-card>
      <el-card>
        <form6 ref="form6"></form6>
      </el-card>
      <el-card>
        <form7 ref="form7"></form7>
      </el-card>
    </div>
    <el-button type="primary" @click="validate">submit</el-button>
  </div>
</template>

<script>
import form1 from "./validateForm/form1";
import form2 from "./validateForm/form2";
import form3 from "./validateForm/form3";
import form4 from "./validateForm/form4";
import form5 from "./validateForm/form5";
import form6 from "./validateForm/form6";
import form7 from "./validateForm/form7";
export default {
  components: {
    form1,
    form2,
    form3,
    form4,
    form5,
    form6,
    form7,
  },
  methods: {
    async validate() {
      const vailRefs = [
        this.$refs.form1,
        this.$refs.form2,
        this.$refs.form3,
        this.$refs.form4,
        this.$refs.form5,
        this.$refs.form6,
        this.$refs.form6,
      ];
      for (const i in vailRefs) {
        const res = await vailRefs[i]?.validate();
        if (!res) {
          return false;
        }
      }
      return true;
    },
  },
};
</script>