0

I am binding a table in a view using a Knockout observable array (self.data) which is populated by an AJAX call and the Knockout Mapping plugin. The aim is to have the ViewModel as a reusable component.

I need to add in a column to select table rows. I want to do this by adding a boolean isSelected observable property to each item in the self.data observable array using mapping options. This observable property is then used by the self.selectClicked function to push or pop items to the self.selectedItems observable array.

Problem is, I'm not quite sure how to add the isSelected property to each array item.

Here is the code at the moment:

//// NOTE: ko.applyBindings and the AJAX call currently happen outside of this code.

function ViewModel() {

var self = this;

var mapping = {
    // Boolean observable property for each array item added here?
};

self.data = ko.observableArray([]);
self.selectedItems = ko.observableArray([]);

self.selectClicked = function (data, event) {

    if (event.currentTarget.checked) {
        self.selectedItems.push(data);                       
    }
    else {
        self.selectedItems.pop(data);
    }

    return true;
};

// AJAX Data is pushed to the self.data observable array through this function
self.addData = function (_data) {

    ko.mapping.fromJS(_data, mapping, self.data);

};
}

1 Answer 1

1

You could manually create the data objects and add isSelected using create:

var mapping = 
{
    create: function(_data) {
        return new Data(_data.data);
    }
};

self.addData = function (_data) {
    ko.mapping.fromJS(_data, mapping, self.data);
};

var Data = function (data) {
    var self = this;

    ko.mapping.fromJS(data, {}, self);

    self.isSelected = ko.observable(false);
};

JsFiddle

This is documented in the Knockout mapping plugin documentation.

Sign up to request clarification or add additional context in comments.

4 Comments

I suspect I have done something wrong somewhere, but I'm getting a ReferenceError: Name is not defined error from Knockout (Name is the first column of the table). I can't see why the solution would be incorrect, but replacing the mapping parameter in ko.mapping.fromJS(_data, mapping, self.data); with {} doesn't cause an issue, so it seems the problem is with the mapping call ('ko.mapping.fromJS(data, {}, self)') in 'Data'.
So Name is coming back from the server? Check the network tab?
The Ajax data is coming back fine, just get the error when including the mapping.
There was a problem with my mapping create function. To get the data, you need to use _data.data. I updated my answer

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.