这是一天的结束,我的大脑已经过夜,但我正在研究如何在动态绑定到Html元素时使用setter。在我到目前为止阅读的很多例子中,下面的Urls似乎对使用具有knockoutjs绑定的setter主题最有帮助,但我仍然没有理解或者理解它应该如何完成。
例如,我的下面的viewmodel(参见fiddle)希望保护私有变量,并且可能稍后通过添加某种验证代码来实现。但是,现在,它只需要获取参数或用户在文本框中输入的文本值。这种操作的最佳语法究竟是什么?
<!-- related bindings: valueUpdate is a parameter for value -->
Your value: <input data-bind="value: someValue, valueUpdate: 'afterkeydown'"/>
答案 0 :(得分:0)
如果你试图实现双向绑定以及验证,那么敲除计算函数应该是最好的方法。 在您的视图模型中有一个私有变量,并为绑定公开ko.computed函数,然后在计算的读/写部分中,您可以进行验证。
答案 1 :(得分:0)
从技术上讲,你可以做到这一点,但这不是Knockout的使用方式。例如,假设我们的viewmodel有一个<select>
和一个文本<input>
绑定。使用私有变量来保存实际值意味着我们需要一个可写的computed
observable来更新它,因为Knockout只将属性绑定到您的视图,而不是私有变量。
function appWithPrivateVars() {
var selectedItem = ko.observable('Option 3'), //our private vars
textVal = ko.observable('Haha');
this.selected = ko.computed({
read: function() { return selectedItem(); },
write: function(value) { /* add validation code here */ selectedItem(value); }
});
this.textVal = ko.computed({
read: function() { return textVal(); },
write: function(value) { /* add validation code here */ textVal(value); }
});
this.listItems = ['Option 1','Option 2','Option 3'];
this.get = function() { return selectedItem(); }; //getter
}
现在比较相同viewmodel 所需的代码,而不关心私有变量(另请注意,您不需要显式的getter / setter):
function appWithProperties() {
var self = this;
this.textVal = ko.observable('Haha');
// example of computed
this.textValInput = ko.computed({
read: function() { return self.textVal(); },
write: function(value) { /* add validation code here */ textVal(value); }
this.selected = ko.observable('Option 3');
this.listItems = ['Option 1','Option 2','Option 3'];
}
问题是你不需要“保护”你可以访问的模型属性,因为如果它们没有绑定到视图,它们将无法被修改。此外,如果您希望在使用var
函数轻松将数据序列化为JSON时使用ko.toJSON
,那么您将遇到麻烦(除非您愿意重写整个解析函数) )。比较两个视图模型的ko.toJSON
输出:
appWithPrivateVars
// no private vars included, eg. 'selectedItem'
{"selected":"Option 1", // computed prop; not what we need
"textVal":"Haha",
"listItems":["Option 1","Option 2","Option 3"]}
了解映射中是否包含“实际”值(这是合乎逻辑的,因为ko.toJSON
无法访问它们)。现在查看appWithProperties
的JSON输出:
{"textVal":"Haha", // actual value
"textValInput: "Haha", // value filter
"selected":"Option 1",
"listItems":["Option 1","Option 2","Option 3"]
}