如果使用扩展器,订阅中的值不会更新

时间:2015-04-22 06:32:28

标签: knockout.js

我在一个observable上调用了extender并且在其中有一个舍入逻辑,并且在它的订阅中也有业务逻辑。问题是当该可观察值的值发生变化时,会调用第一个扩展器并更改值(但不会在视图中更新)。同时调用subscribe,如果在subscribe中更改了同一observable的值,这是最新的更改,但它没有设置为observable。

ko.extenders.scale = function(target, precision) {
    var result = ko.computed({
        read:target,
        write:function(newValue) {
            var that = target;
            if (newValue)
                roundoff(that, precision, newValue);
        }
    }).extend({notify : 'always'});
    result(target());
    return result;
};

self.qty = ko.observable(0).extend({scale:2});

self.qty.subscribe(function() {
    if (self.qty() > self.availQty()) {
        self.qty(0); // This change in not reflected in the view
    }
});

var roundoff = function (targetValue,prec,newValue){
            var current = targetValue(),
            that = targetValue,
            valueToWrite = newValue;
            valueToWrite = isNaN(newValue)?0:parseFloat(+newValue).toFixed(prec);                                                          
            //toFixed may be replaced with other logic in future
            if (valueToWrite !== current) {
                that(valueToWrite);
            } else {
                if (newValue !== current) {
                    that.notifySubscribers(valueToWrite);
                }
            }
        }

2 个答案:

答案 0 :(得分:0)

您应该只使用可写的计算机,而不是使用订阅/扩展程序来完成所有这些操作。为简单起见,我简化了你的'scale'示例,只需使用toFixed ......只需在那里插入你自己的逻辑。

<强>小提琴

http://jsfiddle.net/brettwgreen/fnj27bjj/

<强> HTML:

<input id="qty" data-bind="value: quantityDisplay">

<强> JS

var vm = function() {
    var self = this; 
    self.qty= ko.observable(0).extend({scale:2});
    self.availQty = ko.observable(10);
    self.quantity = ko.observable(0);
    self.quantityDisplay = ko.computed({
        read: function() {
            return parseFloat(self.quantity()).toFixed(2);
        },
        write: function(newValue){
            console.log(newValue);
            if(newValue > self.availQty()){
                    console.log("going zero");
                    self.quantity(0.00);
                }
            else {
                self.quantity(newValue);
            }
        },
        owner: self
    });
}
ko.applyBindings(new vm());

答案 1 :(得分:0)

您有代码来更新值

self.qty(0); // This change in not reflected in the view

没有更新视图。那是因为您还有代码来翻译更新

write:function(newValue) {
    var that = target;
    if (newValue)
        roundoff(that, precision, newValue);
}

如果newValue为“falsy”,则不会更新observable,0是。

所以你只需要将write函数更改为:

write:function(newValue) {
    roundoff(target, precision, newValue);
}