最近阅读项目代码,学习前辈编写angular指令的方式。不涉及关键的业务代码,所以应该没有保密性问题。希望通过写这篇博客明白validator指令是怎么实现的。
像这样使用:
校验功能的实现依赖provider validator和若干directive. provider的结构是这样的:
.provider('validator', [function() {
var validatorFn = function(){//....};
validatorFn.prototype = {//...};
var validator = new validatorFn();
this.$get = function() {return validator;}
}]);
1. form-validator directive
这个指令主要功能:①绑定失焦校验, 执行doValidate; ②当viewValue发生改变时移除错误样式 ③定义dovalidate函数
scope.$apply(scope[formName].$errors);//这是干嘛?
1)每一个directive实例要执行一次link.
2)如果指令没有require ctrl又自己定义了ctrl, 则link中传入的是自己定义的ctrl.
3)form有长度, 是表单元素的数目。
4)watch数组的变化(引用自:http://anjianshi.net/post/yan-jiu-bi-ji/ng-watch):
5)link中的this指向window
6)scope[formName]:值为formController. scope[formName].$setPristine()——重置表单
7) formName.elementName.$viewValue, formName.elementName.$valid
2. form-submit指令:提交的时候执行dovalidate
3.datetimecheck:
读取元素值:attr.ngModel
校验时间区间:if (时间错误) ctrl.$setValidity(validationName, false); 此时ctrl.$error中会有{validationName: true}
4. form-element
ng-repeat中的表单元素必须绑定form-element才能让校验生效,因为ng-repeat生成了新的scope, 在form-validator scope绑定的失焦校验无法适用。
form-validator中的scope是父scope, 而ng-repeat生成新的隔离scope.
综上, datetimechecker, required等指令自定义方法执行$setValidity(), form-submit时,以及元素失焦时(form-validator设置)会执行doValidate来读取ctrl.$error, 从而修改样式。
validator provider设置了默认rules, 开放setRules接口,以及removeError, showError等基本方法。