Knockout.js:使用带有敲除绑定的jquery小部件,这些绑定已经被敲出了绑定

时间:2013-05-31 21:36:34

标签: knockout.js

我的页面部分正在使用敲除UI并在该部分调用ApplyBindings:

HTML

<div id="example">
    <p data-bind="text: message"/>
    <i class="icon-information" title="some tooltip here"/>
</div>

JS

var model = createModel();
ko.applyBindings(model, $("#example")[0]);

我有一个创建的小部件,它也使用了我想要连接到i标签的封面下的Knockout以获得一个很好的工具提示。问题是因为applyBindings基本上在i标签上被调用了两次,所以存在错误。我理解在设计的例子中,我可以将i标签从我的绑定区域移出,但在实际代码中,这很简单是不可能的。

我的问题是人们如何处理这些类型的情况?最简单的答案是将小部件更改为不使用Knockout,但这很糟糕并且是很多额外的代码。

请不要只关注上面的演示代码。这更像是一个理论的例子。尝试使用真实的例子需要太多解释。

2 个答案:

答案 0 :(得分:2)

我认为根据您的小部件的性质,您可以选择几个选项。

第一种方法是使用ko.applyBindingsToNode API,而不是添加“data-bind”属性并从小部件中调用ko.applyBindings

您可以这样称呼:

ko.applyBindingsToNode(element, { someBindings: val, anotherBinding: val2 });

它还接受第三个参数来传递数据上下文,该参数在控制流场景中使用。

以下示例使用此API绑定单独的observable,然后使用“普通”视图模型调用ko.applyBindingshttp://jsfiddle.net/rniemeyer/QBMSB/。肯定有可能以这种方式添加冲突的绑定(两个相同的绑定对不同的值),因此它将以有针对性的方式使用。

如果你正在做一些更像是插入“模板”(一堆HTML)的东西,并且在每个元素上调用ko.applyBindingsToNode并不一定方便,那么你可以使用所描述的技术here防止绑定被应用于儿童。

所以,你会有一个简单的绑定,如:

ko.bindingHandlers.stopBinding = {
    init: function() {
        return { controlsDescendantBindings: true };
    }
};

然后,您的小部件将插入包含此绑定的包装元素。然后,您可以对子项调用applyBindings,而不必担心“正常”的applyBindings调用会干扰。

以下是直接输入小部件标记的示例:http://jsfiddle.net/rniemeyer/Tf79p/。我的假设是你的小部件在调用时会添加这样的标记。

答案 1 :(得分:0)

回复:上面的评论,它并没有打败拥有一个小部件。

在工具提示窗口小部件和模型/视图模型之间创建自定义绑定作为适配器(取决于您正在使用工具提示的方式,或您正在使用的工具提示窗口小部件)。我用这种方式使用jQuery Tools的工具提示(http://jquerytools.org/documentation/tooltip/index.html),只需创建一个简单的自定义绑定处理程序:

ko.bindingHandlers.jqTooltip = {
  init: function (element, valueAccessor) {
     var options = valueAccessor() || {};
     $(element).tooltip();
  }
}

然后在你的装订中:

data-bind="jqTooltip:{}"

或类似的东西,在对象中传递您需要的选项,并调整自定义处理程序以正确地接受这些选项(上面我没有这样做)。

这不应该采用单独的viewmodel,并注意你的viewmodel中可以有很多模型。使用jqDialog,jqButton和其他人查看Ryan Niemeyer的大量示例(google it)。为了重用,可以将它作为一个单独的模型正确地命名空间,并在需要时进行实例化。