我正在尝试创建一个菜单,当您单击代表其中一个组的按钮时,会出现一个图像,显示最受欢迎的产品。我知道这可以更简单,但我正在尝试使用现有的数据模型。
我正在尝试将img元素绑定到属性( ProductImageUrl ),这是嵌套的ko.computed对象( MostPopularProduct )的属性,这是一个父ko.computed对象的属性( SelectedGroup )。
viewModel.SelectedGroup().MostPopularProduct().ProductImageUrl
当页面加载时,一切都按预期工作,数据绑定到图像工作。但是,当我单击Group2按钮时,我收到以下数据绑定错误:
Uncaught TypeError: Unable to parse bindings.
Bindings value: attr:{src: SelectedGroup().MostPopularProduct().ProductImageUrl}
Message: undefined is not a function VM133:3
嵌套的ko.computed属性MostPopularProduct()具有一个值并在页面加载时正确绑定,但在按钮单击后,在更新了父计算属性后,嵌套的ko.computed属性MostPopularProduct()未定义。
我怀疑该问题与viewModel属性的数据绑定有关,该属性是嵌套的ko.computed属性的属性。
这是jsfiddle: http://jsfiddle.net/boaldave/n5KQr/9/
<div id="GroupSelector">
<img data-bind="attr:{src: SelectedGroup().MostPopularProduct().ProductImageUrl}">
<ul id="Menu" data-bind="foreach:Groups">
<li>
<button data-bind="click: $parent.HandleButtonClick">
<span data-bind="text: $data.GroupName"></span>
</button>
</li>
</ul>
</div>
<script>
viewModel = {
Groups:
[
{
GroupName:"Group1",
MostPopularProductID: "Product1"
},
{
GroupName:"Group2",
MostPopularProductID: "Product2"
}
],
Products:
[
{
ProductID: "Product1",
ProductImageUrl: "http://placehold.it/100x100"
},
{
ProductID: "Product2",
ProductImageUrl: "http://placehold.it/200x200"
}
]
};
// Since the data model above comes from a database, I extend the
// viewModel properties with ko.observable and ko.computed properties:
viewModel.SelectedGroupName = ko.observable("Group1");
viewModel.SelectedGroup = ko.computed(function() {
return ko.utils.arrayFirst(viewModel.Groups, function(item) {
return item.GroupName === viewModel.SelectedGroupName();
});
}, viewModel);
viewModel.SelectedGroup().MostPopularProduct = ko.computed(function () {
return ko.utils.arrayFirst(viewModel.Products, function (item) {
return item.ProductID === viewModel.SelectedGroup().MostPopularProductID;
});
}, viewModel);
viewModel.HandleButtonClick = function(s, e) {
viewModel.SelectedGroupName(s.GroupName);
};
var groupSelectorDiv = document.getElementById('GroupSelector');
if (groupSelectorDiv) {
ko.applyBindings(viewModel, groupSelectorDiv);
}
</script>
答案 0 :(得分:1)
JSFiddle:http://jsfiddle.net/jhmRc/
尝试更改
viewModel.SelectedGroup().MostPopularProduct = ko.computed(function () {
到
viewModel.SelectedGroup.MostPopularProduct = ko.computed(function () {
并更改此
<img data-bind="attr:{src: SelectedGroup().MostPopularProduct().ProductImageUrl>
到
<img data-bind="attr:{src: SelectedGroup.MostPopularProduct().ProductImageUrl}>
在您的示例中,您将MostPopularProduct分配给computed的值,这就是它在页面加载时起作用但在值更改后不起作用的原因。
第二种方法是将它添加到计算对象本身