美好的一天
我发现以下两个小提琴完全符合我的要求:
first Fiddle给出了十进制表示法。
second Fiddle为我提供数字数字分组。
我的问题:我如何将它们合并为一个这样我可以像这样使用它:
<b data-bind="commaDecimalFormatter: myNumber">This will output both demical notation and digital grouping</b>
=============================================== ================================================== ================================================== =================
小提琴1代码:
// Formatting Functions
function formatWithComma(x, precision, seperator) {
var options = {
precision: precision || 2,
seperator: seperator || '.'
}
var formatted = parseFloat(x,10).toFixed( options.precision );
var regex = new RegExp(
'^(\\d+)[^\\d](\\d{' + options.precision + '})$');
formatted = formatted.replace(
regex, '$1' + options.seperator + '$2');
return formatted;
}
function reverseFormat(x, precision, seperator) {
var options = {
precision: precision || 2,
seperator: seperator || ','
}
var regex = new RegExp(
'^(\\d+)[^\\d](\\d+)$');
var formatted = x.replace(regex, '$1.$2');
return parseFloat( formatted );
}
// END: Formatting Functions
// Custom Binding - place this in a seperate .js file and reference it in your html
ko.bindingHandlers.commaDecimalFormatter = {
init: function(element, valueAccessor) {
var observable = valueAccessor();
var interceptor = ko.computed({
read: function() {
return formatWithComma( observable() );
},
write: function(newValue) {
observable( reverseFormat(newValue) );
}
});
if( element.tagName == 'INPUT' )
ko.applyBindingsToNode( element , {
value: interceptor
} );
else
ko.applyBindingsToNode( element , {
text: interceptor
} );
}
}
// this is your viewmodel
var vm = {
myNumber: ko.observable(100000)
}
// when the DOM is ready, call ko.applyBindings with your viewmodel
$(function() {
ko.applyBindings(vm);
});
FIDDLE 2代码:
(function(){
var format = function(value) {
toks = value.toFixed(2).replace('-', '').split('.');
var display = '$' + $.map(toks[0].split('').reverse(), function(elm, i) {
return [(i % 3 === 0 && i > 0 ? ',' : ''), elm];
}).reverse().join('') + '.' + toks[1];
return value < 0 ? '-' + display : display;
};
ko.subscribable.fn.money = function() {
var target = this;
var writeTarget = function(value) {
var stripped=value
.replace(/[^0-9.-]/g, '');
target(parseFloat(stripped));
};
var result = ko.computed({
read: function() {
return target();
},
write: writeTarget
});
result.formatted = ko.computed({
read: function() {
return format(target());
},
write: writeTarget
});
result.isNegative = ko.computed(function(){
return target()<0;
});
return result;
};
})();
//Wire it up
$(function() {
var viewModel = {
Cash: ko.observable(1000000).money(),
};
viewModel.Total = ko.computed(function() {
return this.Cash();
}, viewModel).money();
ko.applyBindings(viewModel);
});
答案 0 :(得分:1)
我无法将这两个功能结合起来。请尝试以下操作,因为它可以满足您的需要:Decimal符号和Digit分组:
JS:
function formatPrice(price) {
return price.reverse().replace(/((?:\d{2})\d)/g, '$1 ').reverse();
}
// Need to extend String prototype for convinience
String.prototype.reverse = function() {
return this.split('').reverse().join('');
}
$('.myNumber').each(function(){
$(this).html(formatPrice($(this).html()));
});
请参阅Fiddle
注意:您需要每次刷新浏览器以使jquery将输出值(只读)格式化为数字分组...当然,当您在编辑器屏幕(第一个字段)中输入新值并且您没有看到数字分组更新
答案 1 :(得分:0)
我想提供替代解决方案。您还可以创建一个自定义绑定处理程序,它可以执行您想要的操作(使用您最初提出的语法)。
ko.bindingHandlers. commaDecimalFormatter = {
update: function(element, valueAccessor, allValuesAccessor) {
// This gets the current value of the observable from your model
var value = ko.utils.unwrapObservable(valueAccessor());
// Manipulate `value` as desired using the bodies of the functions you mentioned
// Note: You don't want to use a global function, so actually take the bodies
// and put it here. Plain old JS :)
...
// Set the value on the element
jQuery(element).text(value);
}
};