我正在使用 KnockoutJS 构建一个非常大量的数字应用程序,我希望能够格式化大数字,以便它们以逗号分隔并且看起来不错(xxx,xxx)。
正如您将从下面的 fiddle 中看到的那样,我确实通过使用简单的 RegEx 将绑定(bind)值包装在格式化函数中来实现这一点,但问题是这会覆盖输入中的值并插入 ', ' 转化为基础值(value)。
大数字在应用程序中进一步使用,因此为了防止出现 NaN 错误,我必须将数据属性分配给包含不带“,”的值的输入值,这是存储在 sessionStorage 中的值。
我觉得我的 HTML 标记不必要地膨胀了,我相信我想用 bindingHandler 实现我想要的东西是可能的,但我的绑定(bind)处理程序并不完全存在。
fiddle :http://jsfiddle.net/36sD9/2
formatLargeNumber = function (number) {
if (typeof (number) === 'function') {
return number().toString().replace(/\B(?=(\d{3})+(?!\d))/g, ',');
}
}
ko.bindingHandlers.largeNumber = {
init: function(element, valueAccessor) {
var value = ko.unwrap(valueAccessor());
var interceptor = ko.computed({
read: function() {
return formatLargeNumber(value);
},
write: function(newValue) {
value(reverseFormat(newValue));
}
});
if(element.tagName == 'input' )
ko.applyBindingsToNode(element, {
value: interceptor
});
else
ko.applyBindingsToNode(element, {
text: interceptor
});
}
}
有什么想法吗?
最佳答案
您当前的方法存在多个问题:
element.tagName
返回 INPUT 等,因此在进行比较时需要注意大小写。var value = ko.unwrap(valueAccessor());
您正在解包您的 observable,因此在您的计算中您使用的是它的值而不是函数本身。所以你只需要var value = valueAccessor();
并且你需要在计算的read
方法中调用ko.unwrap
。您不仅需要格式化,还需要在
write
方法中“取消格式化”,但是您的formatLargeNumber
只做格式化方向。您已将
value
和largeNumber
应用于同一输入,这使得两个绑定(bind)相互干扰不要自己编写格式化代码,只需使用已经执行此操作的库即可:http://numeraljs.com/
所以这是使用 numeraljs 绑定(bind)的更正版本:
ko.bindingHandlers.largeNumber = {
init: function(element, valueAccessor) {
var value = valueAccessor();
var interceptor = ko.computed({
read: function() {
return numeral(ko.unwrap(value)).format('0,0');
},
write: function(newValue) {
value(numeral().unformat(newValue));
value.valueHasMutated();
}
}).extend({notify: 'always'});
if(element.tagName.toLowerCase() == 'input' )
ko.applyBindingsToNode(element, {
value: interceptor
});
else
ko.applyBindingsToNode(element, {
text: interceptor
});
}
}
然后像这样使用它:
<input data-bind="largeNumber: testVal">
演示 JSFiddle .
关于javascript - 用于逗号分隔数字的 Knockout bindingHandler,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23180385/