3

I am trying to restrict input as numbers on below fields

Postal Code:
<input type="text" id="zipCode1" name="zipCode1" size="4" maxlength="5" ng-model="zipCode1" ng-change="myNumbers(zipCode1)" />
<input type="text" id="zipCode2" name="zipCode2" size="3" maxlength="4" ng-model="zipCode2" ng-change="myNumbers(zipCode2)" />

it doesn't work with

$scope.myNumbers = function(fieldName){
var tN = fieldName.replace(/[^\d]/g, "");
    if(tN != fieldName)
    fieldName = tN
};

It works with below code but changing both the fields

$scope.$watch('myNumbers', function() {
var tN = $scope.myNumbers.replace(/[^\d]/g, "");
    if(tN != $scope.myNumbers)
    $scope.myNumbers = tN;
})

Need to change the value for the input field where user is typing and not both

Hamed Ali Khan
  • 1,108
  • 3
  • 23
  • 29
  • use data-ng-model instead of ng-model .. and it validates automatically. you should not call any function i guess – bring2dip Jan 29 '14 at 13:36
  • hi refer mentioned link: http://stackoverflow.com/questions/16091218/angularjs-allows-only-numbers-to-be-typed-into-a-text-box i think its help to you.. – Karthi Shan Jan 29 '14 at 13:43
  • You should read the angular documentation on [form validation](http://docs.angularjs.org/api/ng.directive:form). There you will learn how angular validate fields using CSS. – Edwin Dalorzo Jan 29 '14 at 13:45
  • @Edwin Dalorzo 'ng-change' is getting called but the value is not getting assigned using 'fieldName = tN' – Hamed Ali Khan Jan 29 '14 at 13:46

3 Answers3

4

Use the directive found here: https://stackoverflow.com/a/19675023/149060 instead of the ng-change function. Replicated here for easy reference:

angular.module('app').
  directive('onlyDigits', function () {

    return {
        restrict: 'A',
        require: '?ngModel',
        link: function (scope, element, attrs, ngModel) {
            if (!ngModel) return;
            ngModel.$parsers.unshift(function (inputValue) {
                var digits = inputValue.split('').filter(function (s) { return (!isNaN(s) && s != ' '); }).join('');
                ngModel.$viewValue = digits;
                ngModel.$render();
                return digits;
            });
        }
    };
});
Community
  • 1
  • 1
Pauli Price
  • 4,187
  • 3
  • 34
  • 62
  • What's the IE8 behavior? Is it missing something that can be added as a shim? – Pauli Price Jan 29 '14 at 14:13
  • It is taking characters as well where as in other browsers it is taking only digits, any idea? – Hamed Ali Khan Jan 29 '14 at 14:17
  • Probably related to this behavior difference in split: http://stackoverflow.com/a/6425425/149060 - maybe modify the split().join() line into separate statements? – Pauli Price Jan 29 '14 at 14:31
  • 1
    I changed one line of code and it works in all the browsers, `var digits = inputValue.split('').filter(function (s) { return (!isNaN(s) && s != ' '); }).join('');` to `var digits = inputValue.replace(/[^\d]/g, "");` – Hamed Ali Khan Jan 30 '14 at 04:29
2

You could try adding to the inputs

ng-pattern='/^\d{2}$/'
TestersGonnaTest
  • 1,017
  • 2
  • 9
  • 21
  • 7
    Although, that would not prevent you from entering numbers. That would simply mark the field as invalid when the wrong input is given. – Edwin Dalorzo Jan 29 '14 at 13:39
  • @EdwinDalorzo - You're so right! ng-pattern is a bit misleading to beginners. – Davis Aug 25 '14 at 18:01
2

Here is a directive I've done to restrict the keys allowed.

angular.module('app').directive('restrictTo', function() {
    return {
        restrict: 'A',
        link: function (scope, element, attrs) {
            var re = RegExp(attrs.restrictTo);
            var exclude = /Backspace|Enter|Tab|Delete|Del|ArrowUp|Up|ArrowDown|Down|ArrowLeft|Left|ArrowRight|Right/;

            element[0].addEventListener('keydown', function(event) {
                if (!exclude.test(event.key) && !re.test(event.key)) {
                    event.preventDefault();
                }
            });
        }
    }
});

And the input would look like:

<input type="text" name="zipCode1" maxlength="5" ng-model="zipCode1" restrict-to="[0-9]">

The regular expression evaluates the pressed key, not the value.

It also works perfectly with inputs type="number" because prevents from changing its value, so the key is never displayed and it does not mess with the model.

ragnar
  • 1,252
  • 11
  • 18