Format telephone and credit card numbers in AngularJS

前端 未结 17 2062
猫巷女王i
猫巷女王i 2020-11-30 18:29

Question one (formatting telephone number):

I\'m having to format a telephone number in AngularJS but there is no filter for it. Is there a way to u

相关标签:
17条回答
  • 2020-11-30 19:00

    I modified the code to output phone in this format Value: +38 (095) 411-22-23 Here you can check it enter link description here

        var myApp = angular.module('myApp', []);
    
    myApp.controller('MyCtrl', function($scope) {
      $scope.currencyVal;
    });
    
    myApp.directive('phoneInput', function($filter, $browser) {
        return {
            require: 'ngModel',
            link: function($scope, $element, $attrs, ngModelCtrl) {
                var listener = function() {
                    var value = $element.val().replace(/[^0-9]/g, '');
                    $element.val($filter('tel')(value, false));
                };
    
                // This runs when we update the text field
                ngModelCtrl.$parsers.push(function(viewValue) {
                    return viewValue.replace(/[^0-9]/g, '').slice(0,12);
                });
    
                // This runs when the model gets updated on the scope directly and keeps our view in sync
                ngModelCtrl.$render = function() {
                    $element.val($filter('tel')(ngModelCtrl.$viewValue, false));
                };
    
                $element.bind('change', listener);
                $element.bind('keydown', function(event) {
                    var key = event.keyCode;
                    // If the keys include the CTRL, SHIFT, ALT, or META keys, or the arrow keys, do nothing.
                    // This lets us support copy and paste too
                    if (key == 91 || (15 < key && key < 19) || (37 <= key && key <= 40)){
                        return;
                    }
                    $browser.defer(listener); // Have to do this or changes don't get picked up properly
                });
    
                $element.bind('paste cut', function() {
                    $browser.defer(listener);
                });
            }
    
        };
    });
    myApp.filter('tel', function () {
        return function (tel) {
            console.log(tel);
            if (!tel) { return ''; }
    
            var value = tel.toString().trim().replace(/^\+/, '');
    
            if (value.match(/[^0-9]/)) {
                return tel;
            }
    
            var country, city, num1, num2, num3;
    
            switch (value.length) {
                case 1:
                case 2:
                case 3:
                    city = value;
                    break;
    
                default:
                    country = value.slice(0, 2);
                    city = value.slice(2, 5);
                    num1 = value.slice(5,8);
                    num2 = value.slice(8,10);
                    num3 = value.slice(10,12);            
            }
    
            if(country && city && num1 && num2 && num3){
                return ("+" + country+" (" + city + ") " + num1 +"-" + num2 + "-" + num3).trim();
            }
            else if(country && city && num1 && num2) {
                return ("+" + country+" (" + city + ") " + num1 +"-" + num2).trim();
            }else if(country && city && num1) {
                return ("+" + country+" (" + city + ") " + num1).trim();
            }else if(country && city) {
                return ("+" + country+" (" + city ).trim();
            }else if(country ) {
                return ("+" + country).trim();
            }
    
        };
    });
    
    0 讨论(0)
  • 2020-11-30 19:01

    I created an AngularJS module to handle this issue regarding phonenumbers for myself with a custom directive and accompanying filter.

    jsfiddle example: http://jsfiddle.net/aberke/s0xpkgmq/

    Filter use example: <p>{{ phonenumberValue | phonenumber }}</p>

    Filter code:

    .filter('phonenumber', function() {
        /* 
        Format phonenumber as: c (xxx) xxx-xxxx
            or as close as possible if phonenumber length is not 10
            if c is not '1' (country code not USA), does not use country code
        */
    
        return function (number) {
            /* 
            @param {Number | String} number - Number that will be formatted as telephone number
            Returns formatted number: (###) ###-####
                if number.length < 4: ###
                else if number.length < 7: (###) ###
    
            Does not handle country codes that are not '1' (USA)
            */
            if (!number) { return ''; }
    
            number = String(number);
    
            // Will return formattedNumber. 
            // If phonenumber isn't longer than an area code, just show number
            var formattedNumber = number;
    
            // if the first character is '1', strip it out and add it back
            var c = (number[0] == '1') ? '1 ' : '';
            number = number[0] == '1' ? number.slice(1) : number;
    
            // # (###) ###-#### as c (area) front-end
            var area = number.substring(0,3);
            var front = number.substring(3, 6);
            var end = number.substring(6, 10);
    
            if (front) {
                formattedNumber = (c + "(" + area + ") " + front);  
            }
            if (end) {
                formattedNumber += ("-" + end);
            }
            return formattedNumber;
        };
    });
    

    Directive use example:

    <phonenumber-directive placeholder="'Input phonenumber here'" model='myModel.phonenumber'></phonenumber-directive>
    

    Directive code:

    .directive('phonenumberDirective', ['$filter', function($filter) {
        /*
        Intended use:
            <phonenumber-directive placeholder='prompt' model='someModel.phonenumber'></phonenumber-directive>
        Where:
            someModel.phonenumber: {String} value which to bind only the numeric characters [0-9] entered
                ie, if user enters 617-2223333, value of 6172223333 will be bound to model
            prompt: {String} text to keep in placeholder when no numeric input entered
        */
    
        function link(scope, element, attributes) {
    
            // scope.inputValue is the value of input element used in template
            scope.inputValue = scope.phonenumberModel;
    
            scope.$watch('inputValue', function(value, oldValue) {
    
                value = String(value);
                var number = value.replace(/[^0-9]+/g, '');
                scope.phonenumberModel = number;
                scope.inputValue = $filter('phonenumber')(number);
            });
        }
    
        return {
            link: link,
            restrict: 'E',
            scope: {
                phonenumberPlaceholder: '=placeholder',
                phonenumberModel: '=model',
            },
            // templateUrl: '/static/phonenumberModule/template.html',
            template: '<input ng-model="inputValue" type="tel" class="phonenumber" placeholder="{{phonenumberPlaceholder}}" title="Phonenumber (Format: (999) 9999-9999)">',
        };
    }])
    

    Full code with module and how to use it: https://gist.github.com/aberke/042eef0f37dba1138f9e

    0 讨论(0)
  • 2020-11-30 19:01

    Try using phoneformat.js (http://www.phoneformat.com/), you can not only format phone number based on user locales (en-US, ja-JP, fr-FR, de-DE etc) but it also validates the phone number. Its very robust library based on googles libphonenumber project.

    0 讨论(0)
  • 2020-11-30 19:01

    You will need to create custom form controls (as directives) for the phone number and the credit card. See section "Implementing custom form control (using ngModel)" on the forms page.

    As Narretz already mentioned, Angular-ui's Mask directive should help get you started.

    0 讨论(0)
  • 2020-11-30 19:05

    I solved this problem with a custom Angular filter as well, but mine takes advantage of regex capturing groups and so the code is really short. I pair it with a separate stripNonNumeric filter to sanitize the input:

    app.filter('stripNonNumeric', function() {
        return function(input) {
            return (input == null) ? null : input.toString().replace(/\D/g, '');
        }
    });
    

    The phoneFormat filter properly formats a phone number with or without the area code. (I did not need international number support.)

    app.filter('phoneFormat', function() {
        //this establishes 3 capture groups: the first has 3 digits, the second has 3 digits, the third has 4 digits. Strings which are not 7 or 10 digits numeric will fail.
        var phoneFormat = /^(\d{3})?(\d{3})(\d{4})$/;
    
        return function(input) {
            var parsed = phoneFormat.exec(input);
    
            //if input isn't either 7 or 10 characters numeric, just return input
            return (!parsed) ? input : ((parsed[1]) ? '(' + parsed[1] + ') ' : '') + parsed[2] + '-' + parsed[3];
        }
    });
    

    Use them simply:

    <p>{{customer.phone | stripNonNumeric | phoneFormat}}</p>
    

    The regex for the stripNonNumeric filter came from here.

    0 讨论(0)
  • 2020-11-30 19:06

    Find Plunker for Formatting Credit Card Numbers using angularjs directive. Format Card Numbers in xxxxxxxxxxxx3456 Fromat.

    angular.module('myApp', [])
    
       .directive('maskInput', function() {
        return {
                require: "ngModel",
                restrict: "AE",
                scope: {
                    ngModel: '=',
                 },
                link: function(scope, elem, attrs) {
                    var orig = scope.ngModel;
                    var edited = orig;
                    scope.ngModel = edited.slice(4).replace(/\d/g, 'x') + edited.slice(-4);
    
                    elem.bind("blur", function() {
                        var temp;
                        orig  = elem.val();
                        temp = elem.val();
                        elem.val(temp.slice(4).replace(/\d/g, 'x') + temp.slice(-4));
                    });
    
                    elem.bind("focus", function() {
                        elem.val(orig);
                   });  
                }
           };
       })
      .controller('myCtrl', ['$scope', '$interval', function($scope, $interval) {
        $scope.creditCardNumber = "1234567890123456";
      }]);
    
    0 讨论(0)
提交回复
热议问题