问题
I have directive like this:
.directive('noWhitespace', ['$parse', function($parse) {
return {
restrict: 'A',
require: 'ngModel',
link: function (scope, element, attrs, ngModel) {
/*
scope.$watch(attrs.ngModel, function(value) {
var getter = $parse(value);
update(getter(scope));
});
*/
function update(viewValue) {
console.log(JSON.stringify(viewValue));
if (viewValue.match(/\s/)) {
ngModel.$setValidity('whitespace', false);
return undefined;
} else {
ngModel.$setValidity('whitespace', true);
return viewValue;
}
}
ngModel.$parsers.unshift(update);
}
};
}])
and when I use it like this:
<form name="something" novalidate>
<input ng-model="myValue" no-whitespace/>
<div ng-show="something.myValue.$error.whitespace">
Error
</div>
</form>
and I type something and then few spaces at the end update
is not called until I type character after those spaces and then I got error that I have whitespace. (the same happen when I put spaces at the begining or only spaces). Why is that, and how to fix it? As you see in comments I've try to use $watch+$parse
but got error Cannot read property 'match' of undefined
.
回答1:
Try this in your template:
<form name="something" novalidate>
<input ng-model="myValue" no-whitespace ng-trim="false"/>
<div ng-show="something.myValue.$error.whitespace">
Error
</div>
</form>
That should solve the issue of ng-model not updating when you enter empty space.
EDIT: Derp, the attribute goes in the input element not in the div ...
回答2:
This is the expected behavior of model parsers in angular, the idea being that if the entered text is incorrect (has whitespace in the end), the ngModel
should return undefined
. When you think about it, why would you save a value to ngModel
anyway if it's not correct according to your validations?
This is the relevant bit:
if (viewValue.match(/\s/)) {
ngModel.$setValidity('whitespace', false);
return undefined;
}
You are setting validity to false and returning undefined
.
You can keep the model updated even if its value isn't validated by just returning viewValue
always:
if (viewValue.match(/\s/))
ngModel.$setValidity('whitespace', false);
else
ngModel.$setValidity('whitespace', true);
// Return viewvalue regardless of whether it validates or not
return viewValue;
来源:https://stackoverflow.com/questions/24060325/ngmodel-parsers-ingore-whitespace-at-the-end-of-ng-model-value