-
Notifications
You must be signed in to change notification settings - Fork 3.4k
forms: validation. don't show errors until the user has had a chance to do something #1633
Comments
Sorry, just realized that it doesn't greet the user with a bunch of red. However, it goes red as soon as focus comes into the input. I would rather wait until |
There is a way to specify when to show an error: By using the |
I hadn't ever heard of issues with the |
Sorry, just realized I never gave the original example here: http://jsbin.com/cadeko/edit |
This turned out to be longer than anticipated, so long story short: Due to some bugs in the current implementation:
This is a bug with setting the touched state of the input. It can be found in input.js#L183-192: element
.on('focus', function(ev) {
containerCtrl.setFocused(true);
// Error text should not appear before user interaction with the field.
// So we need to check on focus also
ngModelCtrl.$setTouched();
if ( isErrorGetter() ) containerCtrl.setInvalid(true);
}) Here is what is going on:
As a result of (5):
|
(Needless to say, that the Bootstrap version (which does not rely on |
Thanks for the explanation @gkalpak. Totally makes sense where this came from. Obviously triggering the digest manually is not an option. In // scope.fc = the ngModelController
// scope.options = something that the directive user can manipulate
scope.$watch(function() {
if (typeof scope.options.validation.show === 'boolean') {
return scope.fc.$invalid && scope.options.validation.show;
} else {
return scope.fc.$invalid && scope.fc.$touched;
}
}, function(show) {
options.validation.errorExistsAndShouldBeVisible = show;
scope.showError = show; // <-- just a shortcut for the longer version for use in templates
}); This is really handy because in templates, people can do something like this (contrived bootstrap example): <div class="form-group" ng-class="{'has-error': showError}"> <!-- <-- notice that -->
<label for="my-input" class="control-label">My Label</label>
<input ng-model="my.model" name="myForm" class="form-control" id="my-input" />
<div ng-messages="fc.$error" ng-if="showError"> <!-- <-- and that -->
<!-- messages here -->
</div>
</div> I think the If it were me, I would do what we're doing in |
@gkalpak regarding issue 5, I'm guessing the reason its thrown into an error state on focus is because, in the docs for example, all the fields have required directive. So you focus the input, it checks to see if its required, but you havent started typing so no value is present yet, throwing into immediate error state. |
@jasonayre: The inputs are invalid from the beginning (because they are required and empty). The problem is when they show their invalidity (which in the intended default case should happen after the first blur, but happens on focus). |
Fixed with SHA 747eb9c |
Thanks @ThomasBurleson :D |
Hi, maybe I did something really wrong but it does not work with 0.8.3 The myForm.myValue.$touched seems to work correctly at the ng-messages block, |
Yes, looks like it doesn't work in 0.8.3. |
+1 |
When a user opens a page that has a bunch of required fields, all they see is a bunch of red. Not very inviting. I would much rather that validation is hidden until
$touched === true
. I would also like to have the ability to control when validation is shown.I appreciate how helpful angular-material is, but I really like that bootstrap allows me to specify when to show validation errors by requiring me to add the
has-error
class myself. This gives me a lot of flexibility.I haven't looked at the implementation for angular-material, but perhaps I could specify a function which would determine whether validation should be visible for a specific field?
However it's done, I just don't want to invite users to my page with a bunch of invalid fields. Let them touch the fields first, then we'll tell them it's invalid if it still is after they've had a chance to do something with it.
The text was updated successfully, but these errors were encountered: