ng-maxlength preventing a valid value from being databound to input field - angularjs

I have the following field in a form:
<input type="text" name="dedicatedstaff" ng-model="staffingRecord.dedicatedStaff"
tabindex="9" ng-pattern="/^[0-9]{0,4}(\.[0-9]{1,2})?$/" ng-maxlength="7" />
The form is to edit an existing record. No matter what value is in the existing record, the field fails validation and the databind becomes undefined. Some example values that exist on the records are 1, 2.5, 12.5, 99.25, 4.0. I believe every one of these should pass both the pattern and maxlength validations, but it isn't working. I've checked the model and the values are present when loading the form.
When I remove the ng-maxlength directive and just have the ng-pattern, it works fine and those values pass validation. If I remove ng-pattern and just have max-length, it fails. It also doesn't matter if the INPUT is of type text or number. If ng-maxlength is present, it fails. Browser also does not make a difference (tested Chrome, IE & Firefox). I have also verified that it is the maxlength error in the error list.
I am also using ng-maxlength with almost every other field on this particular form, and they also work just fine. And if I type the exact values listed above after form load when ng-maxlength is present validates fine at that point. But that's not a reasonable workflow to make the client type the values over again every time they load the form.
I don't understand it as I use this same pattern in other forms within the app and they work fine. I can get by with just ng-pattern on this particular field, but I would much rather figure out why, in this one case, it won't validate properly on load.
I'm using AngularJS 1.2.14, with JQuery 1.9.1.

I figured it out. It was actually the INPUT type after all. After further testing, I realized my initial test of that variation was incorrect. Changing the INPUT type to NUMBER fixed the validation issues.
<input type="number" name="dedicatedstaff" ng-model="staffingRecord.dedicatedStaff"
tabindex="9" ng-pattern="/^[0-9]{0,4}(\.[0-9]{1,2})?$/" ng-maxlength="7" />

Related

access angularjs form field that contains a number

I have a list of form fields that are generated as the result of an ng-repeat . As such I use the {{$index}} of the repeat loop to name the fields, i.e. ` which leads to:
<input name="myInput0">
<input name="myInput1">
<input name="myInput2">
...
etc. Now I'm trying to access the fields' $valid attribute from the form in the standard angularjs way i.e. myForm.myInput{{$index}}.$valid which resolves to e.g. myForm.myInput0.$valid which I understand won't work because it's accessing a variable and numbers won't be allowed.
However I then tried to access it with myForm['myInput{{$index}}'].$valid, e.g. myForm['myInput0'].$valid which I thought might work but still doesn't. Is there any way possible to access the form field when it contains a numeral? (or other illegal char like a hyphen)?
e: I'm using angularjs 1.2 which might explain why this isn't working. Does anyone know of a workaround for pre 1.3 angular?
The correct expression will look like myForm['myInput' + $index].$valid
I can think of two ways of workaround.
First option:
Put a ng-change on each input and validates it there manually.
Second option:
Retrieve all input elements, interate over each and validates manually
You can get them with this
var inputs = $document[0].querySelectorAll('#rankingForm input');

Angular validation: if dynamically add required attribute validation will break

Trying to dynamically add validation to input file if I choose first option from select. But if I add required attribute, it still ng-valid in class. If I load file to input file, it still ng-empty.
What's wrong? http://plnkr.co/edit/pjyCULes60jWf7yqNsyB?p=preview
The form validation in AngularJS depends on the ngModel attribute, which doesn't work with input type=file.
To solve this, either use ngFileUpload which helps you solve other problems you'll encounter with file upload in Angular as well, or see this or that answer.

Validation Issue in IE 11 when same ng-model in multiple form set to required

The application I am working on has multiple tabs, each tab contains a form with ng-submit. And they share some common fields for example: selectedService.
It's been set to required in both forms. However updating it in one form then switch to another form, Chrome wouldn't complaint it's required since it already has value, however IE 11 complaints that it's required although it already has data entered and angular indicates that it's valid as well.
Is there anyway that I can update IE to let it know that this model has been updated and it has value? Or it's the form needs re-validation?
---------------------Update--------------
I am finally able to replicate it: http://plnkr.co/edit/Gjphya?p=preview
So if you select a value in the first dropdown and click submit in the second row, it says it's required. This only happens in IE, not in Chrome or other browsers.
And I think the problem is around this line:
$scope.selectedService = null;
Thanks!
All I need to fix is to add this line in the select tag:
<option value="">Please Select...</option>
If I init the ng-model in controller, it also fix the issue, however sometimes it causes unexpected issue if the dropdown is binded to an array instead of object collection.

AngularJS - Form validation triggered on load

I added field validation attributes like "required" and "pattern" in my form, and the form is inside a ng-controller. The validation works. But it seems the validations are triggered on page load, and I see all the fields are marked as invalid with error message when the page load.
I tried to add "novalidation" attribute to the form as indicated in the examples on AngularJS website, but no luck.
I would like to have the validation triggered the first time the user tries to interact with it. How can I do that?
Update
Here's an example https://jsfiddle.net/davidshen84/00t197gx/
<div class="mdl-cell mdl-cell-6-col mdl-textfield mdl-js-textfield">
<input class="mdl-textfield__input" type="text" id="screenname" pattern="[a-zA-Z0-9]{3,}" ng-model="comment.screenname" required/>
<label class="mdl-textfield__label" for="screenname">Screen Name</label>
</div>
On load, you should see all the input fields had a red line under them which indicate they are in the invalid state. And the line turns to blue once validated.
Note: The style on the check button does not work...should not be a concern in the problem.
Angular is going to check the form the same way at any point (load or later) and render the result. If you don't want to display the results on load, add logic to check whether the form has been interacted with. You can hide your error messages using ng-if="yourFormName.$dirty", or display according to the status of an individual field with yourFormName.yourFieldName.$dirty.
Click here for live demo.
What is currently implemented (wrong IMHO) is that MDL automatically validates input and doesn't mind "novalidate" form attribute. I had to implement check for empty input value (skip validation and remove is-invalid class) and, since angular form validation requires "novalidate" attribute, check:
if (input.form.novalidate = true) // skip validation
that way you can actually turn off mdl validation and leave everything to angular.
One more thing is actually required. You can create angular directive which validates expression and add is-invalid class if necessary:
div class="mdl-textfield" mdl-validator="form.email.$error"

Angularjs dropdownlist and form validation

I have a page with several dropdown lists and some of them may have default entries that are not valid. It's essentially the same problem that was described here:
AngularJs doesn't validate a invalid dropdown selection
However, I think there has to be a reasonable way to accomplish this without having to check everything manually in the controller. I'd like to be able to do something like this:
<select ng-model="thisEntry" ng-options="option for option in goodOptions"></select>
<span class="error" ng-show="goodOptions.indexOf(thisEntry) == -1">Please select a valid entry from the list</span>
that also sets the form invalid so the user can't submit until it's fixed . The code above actually displays the message, but I don't know how to set the form invalid at the same time, or even in an equivalent line of code. This seems like the equivalent of a blank entry on a form that's easily handled without having to resort to javascript code.

Resources