1

I have the requirement to integrate a select2 mulitple select that is populated by a remote service with knockout. Of course, only the selected options should be binded, not the available options as they come from remote.

If the binded element would be a select, it would be an easy task (selectedOptions binding), but in case of input based there is no.

I created a change event that tries to manipulate the knockout observable and it does its job more or less, but it is not the same as a binding, as for example when I instanciate the component on another page in my spa, it is treated as a completly new instance and I would have to manually synchronize the selected options, work that usually does knockout...

My code

var CodeItem = function(code) {
    this.code = ko.observable(code);
};

self.values =  ko.observableArray([]);
self.selectedIPCs = ko.observableArray([]);


$(".ipcMulti").select2({
                placeholder: "enter ipc",
                minimumInputLength: 2,
                multiple: true,
                id: function(obj) {
                    return obj;
                },
                ajax: { 
                    url: "/assets/Content/suggest_ipcr.json",
                    dataType: 'json',
                    data: function (term, page) {
                        return {
                            q: term // search term
                            //page_limit: 10,
                        };
                    },
                    quietMillis:100,
                    results: function (data, page) {
                        return {results: data.spellcheck.suggestions[1].suggestion};
                    }
                }
            });


            $(".ipcMulti").on("change",function(e){
                underlyingArray = self.selectedIPCs();
                if (e.added !== undefined) {
                    underlyingArray.push(new CodeItem(e.added));
                } else if (e.removed !== undefined) {
                    var todelete =  null;
                    ko.utils.arrayForEach(self.selectedIPCs(), function(item) {
                        var o1 =   e.removed;
                        var value = item.code();
                        if (o1==value) {
                            todelete = item;
                        }
                    });
                    ko.utils.arrayRemoveItem(underlyingArray, todelete);
                }
            });
4

0 回答 0