angular-mask
Version:
Personalized input masks for AngularJS
105 lines (86 loc) • 2.9 kB
JavaScript
;
angular.module('ui.utils.masks.global.percentage', [
'ui.utils.masks.helpers'
])
.directive('uiPercentageMask',
['$locale', '$parse', 'PreFormatters', 'NumberMasks', 'NumberValidators',
function ($locale, $parse, PreFormatters, NumberMasks, NumberValidators) {
function preparePercentageToFormatter (value, decimals) {
return PreFormatters.clearDelimitersAndLeadingZeros((parseFloat(value)*100).toFixed(decimals));
}
return {
restrict: 'A',
require: '?ngModel',
link: function (scope, element, attrs, ctrl) {
var decimalDelimiter = $locale.NUMBER_FORMATS.DECIMAL_SEP,
thousandsDelimiter = $locale.NUMBER_FORMATS.GROUP_SEP,
decimals = parseInt(attrs.uiPercentageMask);
if (!ctrl) {
return;
}
if (angular.isDefined(attrs.uiHideGroupSep)){
thousandsDelimiter = '';
}
if(isNaN(decimals)) {
decimals = 2;
}
var numberDecimals = decimals + 2;
var viewMask = NumberMasks.viewMask(decimals, decimalDelimiter, thousandsDelimiter),
modelMask = NumberMasks.modelMask(numberDecimals);
ctrl.$formatters.push(function(value) {
if(!value) {
return value;
}
var valueToFormat = preparePercentageToFormatter(value, decimals);
return viewMask.apply(valueToFormat) + ' %';
});
function parse(value) {
if(!value) {
return value;
}
var valueToFormat = PreFormatters.clearDelimitersAndLeadingZeros(value) || '0';
if(value.length > 1 && value.indexOf('%') === -1) {
valueToFormat = valueToFormat.slice(0,valueToFormat.length-1);
}
var formatedValue = viewMask.apply(valueToFormat) + ' %';
var actualNumber = parseFloat(modelMask.apply(valueToFormat));
if (ctrl.$viewValue !== formatedValue) {
ctrl.$setViewValue(formatedValue);
ctrl.$render();
}
return actualNumber;
}
ctrl.$parsers.push(parse);
if (attrs.uiPercentageMask) {
scope.$watch(attrs.uiPercentageMask, function(decimals) {
if(isNaN(decimals)) {
decimals = 2;
}
numberDecimals = decimals + 2;
viewMask = NumberMasks.viewMask(decimals, decimalDelimiter, thousandsDelimiter);
modelMask = NumberMasks.modelMask(numberDecimals);
parse(ctrl.$viewValue || '');
});
}
if(attrs.min){
ctrl.$parsers.push(function(value) {
var min = $parse(attrs.min)(scope);
return NumberValidators.minNumber(ctrl, value, min);
});
scope.$watch('min', function(value) {
NumberValidators.minNumber(ctrl, ctrl.$modelValue, value);
});
}
if(attrs.max) {
ctrl.$parsers.push(function(value) {
var max = $parse(attrs.max)(scope);
return NumberValidators.maxNumber(ctrl, value, max);
});
scope.$watch('max', function(value) {
NumberValidators.maxNumber(ctrl, ctrl.$modelValue, value);
});
}
}
};
}
]);