有没有办法从任何父母访问子视图模型?我的用例是我有一些自定义的淘汰组件。我在单独的文件中有每个组件的基本定义。我希望能够以不同的方式自定义它们,具体取决于它所使用的站点的哪个部分。这可能吗?有很多关于如何从孩子访问父视图模型但没有相反的文档。
所以我希望能够做到这样的事情:
parentViewModel.someChildModel.someProperty(someValue);
答案 0 :(得分:4)
我发现这样做的方法是让父虚拟机构建子虚拟机,然后将子虚拟机作为参数注入子组件,方法是将子节点定义为:
ko.components.register("child", {
viewModel: {
createViewModel: function(params, componentInfo) {
return params.viewModel;
}
},
template: {
element: 'child-template'
}
});
子组件使用createViewModel
函数,而不是定义特定的构造函数或实例,该函数使用" viewModel" component param作为viewmodel。 (为安全起见,可以在这里检查是否提供了视图模型,并且它是预期的类)
然后,父虚拟机可以简单地构建子虚拟机,因此可以完全访问它们及其属性。 (例如self.child = new ChildVM()
)
最后,模板必须实际将ViewModel提供给子组件:
<child params="viewModel: child"></child>
它涉及一些样板,但它是我发现从父母到孩子沟通的最佳方式。
完整示例:
function ParentVM() {
var self = this;
self.message = ko.observable();
var callback = function (message) {
self.message(message);
}
self.children = ["foo", "bar"].map(function (text) {
return new ChildVM(text, callback);
});
}
function ChildVM(text, callback) {
var self = this;
self.text = text;
self.onClick = function () {
callback(text + " clicked");
}
}
vm = {};
ko.components.register("parent", {
viewModel: ParentVM,
template: {
element: 'parent-template'
}
});
ko.components.register("child", {
viewModel: {
createViewModel: function(params, componentInfo) {
return params.viewModel;
}
},
template: {
element: 'child-template'
}
});
ko.applyBindings(vm);
&#13;
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.2.0/knockout-min.js"></script>
<parent></parent>
<template id='parent-template'>
<!-- ko foreach: children -->
<child params="viewModel: $data"></child>
<br />
<!-- /ko -->
<span data-bind="text: message"></span>
</template>
<template id='child-template'>
<span data-bind="
text: text,
click: onClick
"></span>
</template>
&#13;