我试图创建一个自定义组件,它有一些应该引用调用者bindingContext的内部标记,因为内部标记引用了调用者$ data和$ parent, 对于$ data,由于模板绑定上的数据选项没有问题,但是它的$ parent呢?
我找到了一个改变ko.bindingContext.prototype [' createChildContext']功能的糟糕解决方案 以这种方式设置自己[" $ parent"]:
self['$parent'] = parentContext['$parent'] === self["$data"] ? parentContext['$parents'][1]:parentContext['$data'];
不知道如何处理自己[' $ parents']:/ 你怎么看待这件事 ? 有干净的方法吗?
提前谢谢 kolja ** jsfiddle示例:https://jsfiddle.net/koljagava/nyh565xp
答案 0 :(得分:0)
I think you want $parentContext
(discussed here).
The node within the child template becomes
<div data-bind="text:variable1 + ' ' + $parentContext.$parents[1].someVariable()">
ko.components.register("parent-component", {
viewModel: function(params) {
this.params = params;
this.someVariable = params.variable;
this.innerContext = {
variable1: "variable1",
logIt: (f) => {
console.log(f);
}
}
},
template: "<!-- ko template: { nodes: $componentTemplateNodes } --><!-- /ko -->"
});
ko.components.register("child-component", {
viewModel: function(params) {
this.params = params;
},
template: "<!-- ko template: { nodes: $componentTemplateNodes, data:$parent} --><!-- /ko -->"
});
ko.applyBindings({
someVariable: ko.observable('someVariableWhoseValueIsHere')
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.0/knockout-min.js"></script>
<parent-component params="variable: someVariable">
<div data-bind="with:innerContext">
<child-component>
<div data-bind="text:variable1 + ' ' + $parentContext.$parents[1].someVariable()">
</child-component>
</div>
</parent-component>
答案 1 :(得分:0)
我找到了一个解决方案:使用ko customBinding
ko.bindingHandlers.withCorrectBinding = {
init: function(element, valueAccessor, allBindings, viewModel, bindingContext) {
var idx = bindingContext.$parents.indexOf(valueAccessor());
//if databinding is not in parents lets ko do normal binding
if (idx === -1)
return;
var childBindingContext = bindingContext.createChildContext(
valueAccessor);
childBindingContext.$parent = null;
childBindingContext.$parents = [];
if (idx+1<bindingContext.$parents.length){
//$parent
childBindingContext.$parent = bindingContext.$parents[idx+1];
//$parents
childBindingContext.$parents = bindingContext.$parents.splice(0,idx);
//$rawData ???
//$parentContext ???
}
ko.applyBindingsToDescendants(childBindingContext, element);
// Also tell KO *not* to bind the descendants itself, otherwise they will be bound twice
return { controlsDescendantBindings: true };
}
};
ko.applyBindings({
var1: "var1Value",
innerContext:{
var2 : "var2Value",
innerInnerContext : {
var3 : "var2Value"
}
}
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.0/knockout-min.js"></script>
<div data-bind="with:innerContext">
<div data-bind="with:innerInnerContext">
<hr/>
<div data-bind="with:$parent">
Does not work<br>
var2 : <div data-bind="text:var2"></div>
var1 : <div data-bind="text:$parent.var1||'not found!'"></div>
</div>
<hr/>
<div data-bind="withCorrectBinding:$parent">
It works!<br>
var2 : <div data-bind="text:var2"></div>
var1 : <div data-bind="text:$parent.var1"||'not found!'></div>
</div>
</div>
</div>