Knockout - 2列表格布局

时间:2015-08-07 19:41:04

标签: html knockout.js html-table

我有下表,我试图循环覆盖范围。我想要2列,每列有不同的行,但是我的代码在每列中重复相同的覆盖。关于如何在不重复的情况下获得2列布局的任何建议?我的foreach绑定应该继续哪个元素?感谢。

        <table class="coverage-table" data-bind="foreach: $root.clientVM.CustomCoverageLines">
            <tr>
                <td>
                    <input type="checkbox" data-bind="checked: Checked" />
                    <label>
                        <span data-bind="text: $data.Description"></span>
                    </label>
                </td>
                <td>
                    <input type="checkbox" data-bind="checked: Checked" />
                    <label>
                        <span data-bind="text: $data.Description"></span>
                    </label>
                </td>
            </tr>
        </table>

2 个答案:

答案 0 :(得分:4)

您可以向模型添加computed属性,以您希望的方式构建数据。请参阅此JSFiddle以获取示例:http://jsfiddle.net/6gvtz51g/。这种方法的一个优点是,如果您愿意,可以指定不同的行大小。

HTML

<table data-bind="foreach: coverageLineRows">
    <tr data-bind="foreach: $data">
        <td>
            <span data-bind="text: $data"></span>
        </td>
    </tr>
</table>

的JavaScript

function ViewModel () {
    var self = this;

    self.coverageLines = ko.observableArray([
        'Medical',
        'Dental',
        'Vision',
        'Life'
    ]);
    self.coverageLineRowSize = ko.observable(2);
    self.coverageLineRows = ko.computed(function () {
        var rows = [];
        var i = 0;
        var lines = self.coverageLines();
        var size = self.coverageLineRowSize();

        while (i < lines.length) {
            rows.push(lines.slice(i, i += size));
        }

        return rows;
    });
}

ko.applyBindings(new ViewModel());

答案 1 :(得分:0)

您如何看待这个解决方案?它不像@JackieChiles给出的解决方案那样灵活,因为它需要一些调整来处理不同数量的行。但是,我提供的代码确实为两列提供了更漂亮的外观,并且还能够跟踪每个项目旁边的复选框。我怀疑我们的解决方案的组合将在您的最终产品中:)

    var vm = function () {
    var self = this;

    this.array = ko.observableArray([{
        name: ko.observable('Medical'),
        checked: ko.observable()
    }, {
        name: ko.observable('Dental'),
        checked: ko.observable()
    }, {
        name: ko.observable('Vision'),
        checked: ko.observable()
    }, {
        name: ko.observable('Life'),
        checked: ko.observable()
    }, {
        name: ko.observable('Other'),
        checked: ko.observable()
    }]);

    this.coverageSplit = ko.computed(function () {
        var retArray = [];
        var i = 0;
        var arrayUnWrapped = this.array();
        while (i < arrayUnWrapped.length) {
            if (i >= arrayUnWrapped.length - 1) {
                retArray.push({
                    col1: arrayUnWrapped[i],
                    col2: {
                        name: '',
                        checked: false,
                        hideThisCheck: true
                    }
                })
                console.log(retArray[retArray.length - 1]);
                break;
            }

            retArray.push({
                col1: arrayUnWrapped[i],
                col2: arrayUnWrapped[i + 1]
            });
            i += 2;
        }

        return retArray;
    });
    this.check_click = ko.observable('None');

    this.setLastClicked = function (name) {
       if (name.length > 0) self.check_click(name);
    };
};

ko.applyBindings(vm);

以下是行动中的小提琴http://jsfiddle.net/ozrevulsion/sva9tnje/