1'use strict'; 2/** 3* General-purpose validator for ngModel. 4* angular.js comes with several built-in validation mechanism for input fields (ngRequired, ngPattern etc.) but using 5* an arbitrary validation function requires creation of a custom formatters and / or parsers. 6* The ui-validate directive makes it easy to use any function(s) defined in scope as a validator function(s). 7* A validator function will trigger validation on both model and input changes. 8* 9* @example <input ui-validate=" 'myValidatorFunction($value)' "> 10* @example <input ui-validate="{ foo : '$value > anotherModel', bar : 'validateFoo($value)' }"> 11* @example <input ui-validate="{ foo : '$value > anotherModel' }" ui-validate-watch=" 'anotherModel' "> 12* @example <input ui-validate="{ foo : '$value > anotherModel', bar : 'validateFoo($value)' }" ui-validate-watch=" { foo : 'anotherModel' } "> 13* 14* @param ui-validate {string|object literal} If strings is passed it should be a scope's function to be used as a validator. 15* If an object literal is passed a key denotes a validation error key while a value should be a validator function. 16* In both cases validator function should take a value to validate as its argument and should return true/false indicating a validation result. 17*/ 18angular.module('ui.validate', []).directive('uiValidate', function () { 19 return { 20 restrict: 'A', 21 require: 'ngModel', 22 link: function (scope, elm, attrs, ctrl) { 23 var validateFn, validators = {}, 24 validateExpr = scope.$eval(attrs.uiValidate); 25 if (!validateExpr) { return; } 26 if (angular.isString(validateExpr)) { 27 validateExpr = { validator: validateExpr }; 28 } 29 angular.forEach(validateExpr, function (exprssn, key) { 30 validateFn = function (valueToValidate) { 31 var expression = scope.$eval(exprssn, { '$value': valueToValidate }); 32 if (angular.isObject(expression) && angular.isFunction(expression.then)) { 33 // expression is a promise 34 expression.then(function () { 35 ctrl.$setValidity(key, true); 36 }, function () { 37 ctrl.$setValidity(key, false); 38 }); 39 return valueToValidate; 40 } else if (expression) { 41 // expression is true 42 ctrl.$setValidity(key, true); 43 return valueToValidate; 44 } else { 45 // expression is false 46 ctrl.$setValidity(key, false); 47 return valueToValidate; 48 } 49 }; 50 validators[key] = validateFn; 51 ctrl.$formatters.push(validateFn); 52 ctrl.$parsers.push(validateFn); 53 }); 54 function apply_watch(watch) { 55 //string - update all validators on expression change 56 if (angular.isString(watch)) { 57 scope.$watch(watch, function () { 58 angular.forEach(validators, function (validatorFn) { 59 validatorFn(ctrl.$modelValue); 60 }); 61 }); 62 return; 63 } 64 //array - update all validators on change of any expression 65 if (angular.isArray(watch)) { 66 angular.forEach(watch, function (expression) { 67 scope.$watch(expression, function () { 68 angular.forEach(validators, function (validatorFn) { 69 validatorFn(ctrl.$modelValue); 70 }); 71 }); 72 }); 73 return; 74 } 75 //object - update appropriate validator 76 if (angular.isObject(watch)) { 77 angular.forEach(watch, function (expression, validatorKey) { 78 //value is string - look after one expression 79 if (angular.isString(expression)) { 80 scope.$watch(expression, function () { 81 validators[validatorKey](ctrl.$modelValue); 82 }); 83 } 84 //value is array - look after all expressions in array 85 if (angular.isArray(expression)) { 86 angular.forEach(expression, function (intExpression) { 87 scope.$watch(intExpression, function () { 88 validators[validatorKey](ctrl.$modelValue); 89 });
90 }); 91 } 92 }); 93 } 94 } 95 // Support for ui-validate-watch 96 if (attrs.uiValidateWatch) { 97 apply_watch(scope.$eval(attrs.uiValidateWatch)); 98 } 99 } 100 }; 101});
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.