Knockout Custom Binder适用于ko.applyBindings之后

时间:2014-01-02 16:33:18

标签: knockout.js

问题:如果绑定器在ApplyBindings()函数之后执行,我如何让绑定器应用它的绑定?

我尝试过以不同方式订购它们,相同的文件,不同的文件等。似乎没有什么工作,我尝试重新应用绑定,它对我大吼大叫每个上下文的多重绑定。

我的观点

@* Page Content *@
<h1><span class="entity-type" data-bind="text: $data[0].EntityType"></span></h1>
<a data-bind="attr: { href: '/Entity/Create?EntityType=' + $data[0].EntityType() }" class="ignore">New</a>
<form>
    <table>
        <thead>
            <tr data-bind="template: { name: 'HeaderRowTemplate', foreach: $data[0].Properties }">
                <td data-bind="text: Name, visible: SummaryProperty"></td>
            </tr>
        </thead>
        <tbody data-bind="template: { name: 'DataRowTemplate', foreach: $data }">

        </tbody>
    </table>
</form>

@section Scripts {  
    @* Templates *@
    <script id="HeaderRowTemplate" type="text/html">
        <td data-bind="text: Name, visible: SummaryProperty"></td>
    </script>

    <script id="DataRowTemplate" type="text/html">
        <tr data-bind="template: { name: 'DataItemTemplate', foreach: Properties }"></tr>
    </script>

    <script id="DataItemTemplate" type="text/html">
        <td data-bind="visible: SummaryProperty">
            <input data-bind="editorFor: Value.ValueAsString" />
        </td>
    </script>
}

我的MVC模型序列化:

@* Scripts *@
<script type="text/javascript">
    function ApplyBindings() {
        var data = @Html.Raw(new System.Web.Script.Serialization.JavaScriptSerializer().Serialize(Model)),
            viewModel = ko.mapping.fromJS(data);
        ko.applyBindings(viewModel);
    }
    ApplyBindings();
</script>

我的自定义活页夹:

ko.bindingHandlers.editorFor = { // Note: Binder is a Work-In-Progress.
    init: function (element, valueAccessor, allBindings, viewModel, bindingContext) {
        var val = valueAccessor(),
            dataType = bindingContext.$data.DataType,
            innerBindingContext = bindingContext.extend(valueAccessor);

        if (dataType() == 'unit') {
            // Bind to a input & dropdown.
            element.outerHTML += "<select data-bind='options: Value.Value.AllowedUnits'></select>";
            ko.applyBindingsToDescendants(innerBindingContext, element);
        } else if (dataType() == 'dropdown') {
            // Bind to a dropdown.
            element.outerHTML = "<select data-bind=\"options: Value.Value.DropDown.Options, optionsText: 'Name', optionsCaption: 'Desciption', value: $data.Value.Value.DropDown.Selected \"></select>";
        } else if (dataType() == 'entity') {
            // TODO: Add logic for entities later.

        } else {
            element.outerHTML = "<input data-bind=\"value: Value.ValueAsString\" />"; // Current Issue Area.
        }

        ko.applyBindingsToDescendants(innerBindingContext, element);
    },
    update: function (element, valueAccessor, allBindings, viewModel, bindingContex) {

    }
}

1 个答案:

答案 0 :(得分:0)

利用淘汰赛的模板引擎将是您最好的选择。

return ko.bindingHandlers.template.init(element, options, allBindingsAccessor, viewModel, bindingContext)

从您的其他绑定处理程序中传递您从原始绑定处理程序收到的参数。显然你可以选择自由,只需确保选项对象包含'name'属性:

{ name: 'name-of-template', data: { foo1: 0, foo2: false } }

此时,您不必使用applyBindingsToAnything。