Knockout.Extensions DataBinding Sample 3

by ducka

HTML

<script src="https://raw.github.com/SteveSanderson/knockout/master/build/output/knockout-latest.js"></script>
<link rel="stylesheet" href="https://raw.github.com/DataTables/DataTables/master/media/css/demo_table_jui.css">
<script src="https://raw.github.com/CogShift/Knockout.Extensions/master/Javascript/src/cog.javascript.js"></script>
<script src="https://raw.github.com/CogShift/Knockout.Extensions/master/Javascript/src/cog.knockout.bindings.dataTables.js"></script>
<script src="https://raw.github.com/DataTables/DataTables/master/media/js/jquery.dataTables.js"></script>
<script src="https://github.com/douglascrockford/JSON-js/blob/master/json2.js"></script>
<!-- Sample 3: Editable Data Table with Row Template and AJAX data source -->
<div Id="sample3" class="sample">
    <h1> Sample 3: Editable Data Table with Row Template and AJAX data source</h1>
    <p class="description">
        This demonstration is the same as Sample 2, except it uses an AJAX datasource instead of an Array datasource.  This shows how the Knockout DataTables adapter
        can support server side processing of paging, sorting, searching, and retrieval of data.
    </p>
    <p>
        Need to implement:
        <ul>
            <li>Search</li>
            <li>Add</li>
            <li>Remove</li>
            <li>Edit and Save</li>
            <li>Cancel perhaps...</li>
            <li>Read Only mode perhaps...</li>
        </ul>
    </p>
    <div class="table">
        <br /><br />
        <table data-bind="dataTable: { dataSource: getData, rowTemplate: 'sample3RowTemplate', columns: ['Column1', 'Column2', 'Column3'] }">
            <thead>
                <tr>
                    <td>Column 1</td>
                    <td>Column 2</td>
                    <td>Column 3</td>
                </tr>
            </thead>
            <tbody>
            </tbody>
        </table>
    </div>
</div>
<script Id="sample3RowTemplate" type="text/html">
    <td><input type="text" data-bind="value:...

CSS

.sample
{
    border:1px solid gray;
    padding:15px;
    margin-top:10px;
    margin-bottom:10px;
}

.sample .description
{
    
}

.sample h1
{
    margin-top: 0px;
    margin-bottom: 20px;
    font-size:1.5em;
}

.sample h2
{
    margin-top: 0px;
    margin-bottom: 5px;
    font-size:1.1em;
}
.sample .table, .sample table
{
    width:800px;
    
}

.sample p 
{
     margin-top:20px;   
     margin-bottom:20px;
}

.sample a
{
     color:blue;
     text-decoration:underline;
     cursor:pointer;   
}

JavaScript

function Record(Id, Column1, Column2, Column3)
    {
        this.Id = Id;
        this.Column1 = ko.observable(Column1);
        this.Column2 = ko.observable(Column2);
        this.Column3 = ko.observable(Column3);
    }

    function ViewModel()
    {
        var cellCounter = 0;
        var idCounter = 0;

        this.data = ko.observableArray([
                    CreateRecord(),
                    CreateRecord(),
                    CreateRecord(),
                    CreateRecord()
                ]);

        this.getData = function (options, callback) {
            $.ajax({
                url: '/BindingsDemo/GetData',
                data: ko.toJSON(options),
                type: "POST",
                contentType: "application/json charset=utf-8",
                dataType: "json",
                success: function (responseData, textStatus, jqXHR) {
                    callback(responseData);
                }
            });
        }

        this.json = ko.dependentObservable(function ()
        {
            return ko.toJSON(this.data);
        }, this);

        this.addItem = function ()
        {
            this.data.push(CreateRecord());
        }

        this.removeLastItem = function ()
        {
            this.data.pop();
        }

        this.removeItem = function (item)
        {
            // Issue: Why is the instance of 'item' not exist in the data array?  Does datatables do something to the objects?
            //            this.data.remove(item);
            this.data.remove(function (item2) { return item.Id == item2.Id; });
        }

        function CreateRecord()
        {
            return new Record(++idCounter, "cell " + ++cellCounter, "cell " + ++cellCounter, "cell " + ++cellCounter);
        }
    };

var vm3 = new ViewModel();

    $(function ()
    {
        ko.applyBindings(vm3, $("#sample3")[0]);
    });