在可观察字段Knocout中显示$符号

时间:2016-08-24 08:06:02

标签: javascript knockout.js currency

在我的MVC项目中,我有一个包含3个计算器的视图,每个计算器都有自己的形式,我有一个适用于所有3种形式的视图模型,视图模型包含多个计算字段,字段相互依赖。

我正在寻找为所有字段添加$符号的方法,我只是需要将它显示给客户端然后在javascript / KO代码中删除它(我无法进行计算在带有$符号的计算字段上。

我写了以下函数:

this.formatCurrency = function (value) {
    if (value && value !== "") {
        value = value.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ",");
        return "$" + value;
    }
}

但是我必须从每个字段调用此函数:

<span data-bind='text: formatCurrency(improvements())'>

还要在计算的任何计算之前删除$符号。

有没有人更清楚如何做到这一点?我没有想出任何东西..

2 个答案:

答案 0 :(得分:1)

文档中的一个示例是在&#34;真实&#34;之上使用ko.pureComputed图层。数值:

this.price = ko.observable(25.99);

this.formattedPrice = ko.pureComputed({
    read: function () {
        return '$' + this.price().toFixed(2);
    },
    write: function (value) {
        // Strip out unwanted characters, parse as float, then write the 
        // raw data back to the underlying "price" observable
        value = parseFloat(value.replace(/[^\.\d]/g, ""));
        this.price(isNaN(value) ? 0 : value); // Write to underlying storage
    },
    owner: this
});

来源:http://knockoutjs.com/documentation/computed-writable.html

这允许您在数据绑定中使用formattedPrice,甚至可以写入它。 price仍然是一个数字。您需要在viewmodel中为每个数字添加额外的属性,但是......

如果它只是您之后的单向绑定,您还可以创建扩展currencyFormatter绑定的text绑定:

&#13;
&#13;
var formatCurrency = function(value) {
  value = parseFloat(("" + value).replace(/[^\.\d]/g, ""));
  return "$" + (isNaN(value) ? 0 : value);
}

ko.bindingHandlers.currencyText = {
  update: function(element, valueAccessor) {
    var originalValue = ko.unwrap(valueAccessor());
    var formatValue = formatCurrency.bind(null, originalValue);
    ko.bindingHandlers.text.update.call(null, element, formatValue);
  }
};


ko.applyBindings({
  source: ko.observable(1)
})
&#13;
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.2.0/knockout-min.js"></script>

<input type="number" step="0.1" data-bind="value: source">
<h1 data-bind="currencyText: source"></h1>
&#13;
&#13;
&#13;

答案 1 :(得分:0)

感谢@ user3297291的回答,我明白了如何做到这一点。

我有以下bindingHandler来处理我的数值:

Angularjs

我添加此行以在获取值时删除$符号:

ko.bindingHandlers.numValue = {
init: function (element, valueAccessor) {
    function numValueHandler() {
        valueAccessor()(this.value);
    }
    $(element).on("input change", numValueHandler)
              .val(ko.unwrap(valueAccessor()));
    ko.utils.domNodeDisposal.addDisposeCallback(element, function () {
        $(element).off("input change", numValueHandler);
    });
},
update: function (element, valueAccessor) {
    element.value =ko.unwrap(valueAccessor());
}
};

在将信号发送回View:

之前添加了一个$符号
parseFloat(("" + this.value).replace(/[^\.\d]/g, ""))

所以整个bindingHandler看起来像这样:

 element.value ='$' + ko.unwrap(valueAccessor());

电话是:

ko.bindingHandlers.numValue = {
init: function (element, valueAccessor) {
    function numValueHandler() {
        valueAccessor()(parseFloat(("" + this.value).replace(/[^\.\d]/g, "")));
    }
    $(element).on("input change", numValueHandler)
              .val(ko.unwrap(valueAccessor()));
    ko.utils.domNodeDisposal.addDisposeCallback(element, function () {
        $(element).off("input change", numValueHandler);
    });
},
update: function (element, valueAccessor) {
    element.value ='$' + ko.unwrap(valueAccessor());
}
};

这完美无缺,无需在每个字段上调用<input type="text" data-bind="numValue: improvements" /> <input type="text" data-bind="numValue: improvements2" /> //etc.. 函数,只需几行代码。

感谢@ user3297291的帮助!