1.获取用户传的rules进行验证,主要是安装了async-validator插件。
2.点击提交按钮验证所有表单,主要是触发了父组件el-form的validate,validate会查找所有el-form-item,然后调用el-form-item的validate。
el-form.vue
methods:{
validate(cb){
let r = this.$broadcast('elFormItem').every(item=>item.validate());
cb(r)
}
}
broadcast的写法
Vue.prototype.$broadcast = function(componentName, name) {
let children = this.$children; // 子组件
let arr = [];
function find(children) {
children.forEach(child => {
if (child.$options.name == componentName) {
arr.push(child);
if(name){
child.$emit(name)
}
}
if (child.$children) {
find(child.$children);
}
})
}
find(children);
return arr
}
3.通过rules里设置的trigger去触发验证的话,实际上是靠子组件,比如el-input进行发布订阅。然后触发el-form-item的validate
el-input.vue
<template>
<input type="text" :value="value" @input="handleInput" />
</template>
<script>
export default {
name: "elInput",
props: {
value: String,
},
methods: {
handleInput(e) {
this.$emit('input',e.target.value)
this.$dispatch('elFormItem','changeValue');
},
},
};
</script>
el-form-item.vue
mounted() {
this.$on("changeValue", () => {
// 需要获取最新的值检测是否合法, 去全部数据中通过prop进行查找
this.validate();
});
}
dispatch的写法
// 告诉组件触发自己身上的哪个方法
Vue.prototype.$dispatch = function(componentName, name) {
let parent = this.$parent; // 父组件 不能是原生dom
while (parent) {
if (componentName == parent.$options.name) {
break;
} else {
parent = parent.$parent;
}
}
if (parent && name) {
parent.$emit(name)
}
return parent;
};