javascript 带有指令的 Angularjs 初始表单验证
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/17011288/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Angularjs initial form validation with directives
提问by GrahamB
I have a validation directive called valid-number
that is used to set the validity of a form using $setValidity - this works fine for any text values that I type into the input box that have the directive applied to as an attribute.
我有一个名为的验证指令valid-number
,用于使用 $setValidity 设置表单的有效性 - 这适用于我在输入框中键入的任何文本值,这些值将指令应用于作为属性。
The HTML is
HTML是
<form name="numberForm">
<input name="amount" type="text" ng-model="amount" required valid-number /></form>
The directive is as follow
指令如下
angular.module('test',[]).directive('validNumber',function(){
return{
require: "ngModel",
link: function(scope, elm, attrs, ctrl){
var regex=/\d/;
ctrl.$parsers.unshift(function(viewValue){
var floatValue = parseFloat(viewValue);
if(regex.test(viewValue)){
ctrl.$setValidity('validNumber',true);
}
else{
ctrl.$setValidity('validNumber',false);
}
return viewValue;
});
}
};
});
However, I would also like the validation to be triggered and set the css to an invalid clsss if the value the input box is initialised to when the page is first loaded is invalid, eg if I set $scope.amount = 'not a number'
I would expect the input box to have had the directive applied to it, but no joy. In order for not a number
to be highlighted as invalid I have to make a change to the contents of the input, which triggers the directive.
但是,如果第一次加载页面时输入框初始化的值无效,我也希望触发验证并将 css 设置为无效的 clsss,例如,如果我设置$scope.amount = 'not a number'
我希望输入框有指令适用于它,但没有喜悦。为了not a number
突出显示为无效,我必须对触发指令的输入内容进行更改。
How can I ensure the directive applies to whatever the <input>
is initialised with?
如何确保指令适用于<input>
初始化的任何内容?
A full code example is here;
完整的代码示例在这里;
回答by Stewie
$parsers
array contains a list of functions that will be applied to the value that model receives from the view (what user types in), and $formatters
array contains the list of functions that are being applied to the model value before it's displayed in the view.
$parsers
array 包含将应用于模型从视图接收的值的函数列表(用户键入的内容),$formatters
array 包含在模型值显示在视图中之前应用于模型值的函数列表。
In your directive you correctly used the $parsers
array, but you also need to add the $formatters
array if you want the initial value to be validated:
在您的指令中,您正确使用了$parsers
数组,但$formatters
如果您希望验证初始值,还需要添加数组:
angular.module('test',[]).directive('validNumber',function(){
return{
require: "ngModel",
link: function(scope, elm, attrs, ctrl){
var regex = /^\d$/;
var validator = function(value){
ctrl.$setValidity('validNumber', regex.test(value));
return value;
};
ctrl.$parsers.unshift(validator);
ctrl.$formatters.unshift(validator);
}
};
});
回答by Blackhole
You can simply call your verification function during the linking phase, like in this fiddle:
您可以在链接阶段简单地调用您的验证函数,就像在这个小提琴中一样:
link: function(scope, elm, attrs, ctrl) {
var regex=/\d/;
var verificationFunction = function(viewValue) {
var floatValue = parseFloat(viewValue);
if(regex.test(viewValue)) {
ctrl.$setValidity('validNumber',true);
return viewValue;
}
else {
ctrl.$setValidity('validNumber',false);
return undefined;
}
};
ctrl.$parsers.unshift(verificationFunction);
verificationFunction();
}
回答by Maxim Zhukov
After (>=) angular 1.3.1 version was released you could implement that behaviour with a little bit correct way, following angular validation directives style (e.g. required, maxlength).
在 (>=) angular 1.3.1 版本发布后,您可以按照 angular 验证指令样式(例如required、maxlength)以正确的方式实现该行为。
In that case you have to append your validator as property of $validators
array and there are no need in $parsers
or $formatters
anymore:
在这种情况下,你必须要附加的验证作为财产$validators
数组,有没有必要$parsers
或$formatters
不再:
var app = angular.module('test', []);
app
.directive('validNumber', function() {
return {
require: "ngModel",
link: function(scope, elm, attrs, ctrl) {
var regex = /^\d+$/;
ctrl.$validators['validNumber'] = function(modelValue, viewValue) {
return regex.test(viewValue);
};
}
};
});
app.controller('NumberCtrl', NumberCtrl);
function NumberCtrl($scope) {
$scope.amount = '5z';
};
input.ng-invalid {
background-color: #FA787E;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.1/angular.min.js"></script>
<div ng-app="test">
<div ng-controller="NumberCtrl">
<div ng-form name="numberForm">
<input name="amount"
type="text"
ng-model="amount"
required
valid-number />
<span ng-show="numberForm.amount.$error.validNumber">
Doesn't look like an integer
</span>
</div>
</div>
</div>