ko select2

by niki4810

HTML

<script src="https://github.com/downloads/SteveSanderson/knockout/knockout-2.1.0.js"></script>
<script src="https://raw.github.com/ivaynberg/select2/master/select2.js"></script>
<h1>Single select</h1>
<select data-bind="options: states, optionsValue: 'id', optionsText: 'text', value: selectSingleState" style="width: 150px"></select>
<select data-bind="options: states, optionsValue: 'id', optionsText: 'text', value: selectSingleState, select2: { }" style="width: 150px"></select>
<div>
    Selected: <span data-bind="text: selectSingleState"></span>
</div>

<h1>Multiple select</h1>
<select multiple="true" data-bind="options: states, optionsValue: 'id', optionsText: 'text', selectedOptions: selectMultipleStates, select2: { }" style="width: 300px"></select>
<div>
    Selected: <span data-bind="text: selectMultipleStates"></span>
</div>

<h1>Select within foreach</h1>
<ul data-bind="foreach: arrayOfStates">
    <li>
        <select data-bind="options: $parent.states, optionsValue: 'id', optionsText: 'text', optionsCaption: ' ', value: state, select2: { placeholder: ' ', allowClear: true }" style="width: 220px"></select>
        <button data-bind="click: $parent.removeState">Remove</button>
    </li>
</ul>
<button data-bind="click: addState">Add</button>
<div>
    Selected: <span data-bind="text: ko.toJSON(arrayOfStates())"></span>
</div>

<h1>Select data via ajax</h1>
<input type="hidden" data-bind="value: selectStateAjax, select2: { minimumInputLength: 1, query: stateQuery }" style="width: 300px">
<div>
    Selected: <span data-bind="text: selectStateAjax"></span>
</div>

CSS

h1 { font-size: 120%; font-weight: bold; margin-top: 0.5em; margin-bottom: 0.25em; }

/* https://github.com/ivaynberg/select2/raw/master/select2.css */

/*
Version: @@ver@@ Timestamp: @@timestamp@@
*/
.select2-container {
    position: relative;
    display: inline-block;
    /* inline-block for ie7 */
    zoom: 1;
    *display: inline;

}

.select2-container,
.select2-drop,
.select2-search,
.select2-container .select2-search input{
  /*
Force border-box so that % widths fit the parent
container without overlap because of margin/padding.
More Info : http://www.quirksmode.org/css/box.html
*/
  -moz-box-sizing: border-box; /* firefox */
  -ms-box-sizing: border-box; /* ie */
  -webkit-box-sizing: border-box; /* webkit */
  -khtml-box-sizing: border-box; /* konqueror */
  box-sizing: border-box; /* css3 */
}

.select2-container .select2-choice {
    background-color: #fff;
    background-image: -webkit-gradient(linear, left bottom, left top, color-stop(0, #eeeeee), color-stop(0.5, white));
    background-image: -webkit-linear-gradient(center bottom, #eeeeee 0%, white 50%);
    background-image: -moz-linear-gradient(center bottom, #eeeeee 0%, white 50%);
    background-image: -o-linear-gradient(bottom, #eeeeee 0%, #ffffff 50%);
    background-image: -ms-linear-gradient(top, #eeeeee 0%, #ffffff 50%);
    filter: progid:DXImageTransform.Microsoft.gradient(startColorstr = '#eeeeee', endColorstr = '#ffffff', GradientType = 0);
    background-image: linear-gradient(top, #eeeeee 0%, #ffffff 50%);
    -webkit-border-radius: 4px;
    -moz-border-radius: 4px;
    border-radius: 4px;
    -moz-background-clip: padding;
    -webkit-background-clip: padding-box;
    background-clip: padding-box;
    border: 1px solid #aaa;
    display: block;
    overflow: hidden;
    white-space: nowrap;
    position: relative;
    height: 26px;
    line-height: 26px;
    padding: 0 0 0 8px;
    color: #444;
    text-decoration: none;
}

.select2-container .select2-choice span {
   ...

JavaScript

ko.bindingHandlers.select2 = {
    init: function(element, valueAccessor) {
        $(element).select2(valueAccessor());

        ko.utils.domNodeDisposal.addDisposeCallback(element, function() {
            $(element).select2('destroy');
        });
    },
    update: function(element) {
        $(element).trigger('change');
    }
};

var StateItem = function(state) {
    this.state = ko.observable(state);
};

var ViewModel = function () {
    var self = this;
    this.states = [
        { id: "AL", text: "Alabama" },
        { id: "AK", text: "Alaska" },
        { id: "AZ", text: "Arizona" },
        { id: "AR", text: "Arkansas" },
        { id: "CA", text: "California" },
        { id: "CO", text: "Colorado" },
        { id: "CT", text: "Connecticut" },
        { id: "DE", text: "Delaware" },
        { id: "FL", text: "Florida" },
        { id: "GA", text: "Georgia" },
        { id: "HI", text: "Hawaii" },
        { id: "ID", text: "Idaho" },
        { id: "IL", text: "Illinois" },
        { id: "IN", text: "Indiana" },
        { id: "IA", text: "Iowa" },
        { id: "KS", text: "Kansas" },
        { id: "KY", text: "Kentucky" },
        { id: "LA", text: "Louisiana" },
        { id: "ME", text: "Maine" },
        { id: "MD", text: "Maryland" },
        { id: "MA", text: "Massachusetts" },
        { id: "MI", text: "Michigan" },
        { id: "MN", text: "Minnesota" },
        { id: "MS", text: "Mississippi" },
        { id: "MO", text: "Missouri" },
        { id: "MT", text: "Montana" },
        { id: "NE", text: "Nebraska" },
        { id: "NV", text: "Nevada" },
        { id: "NH", text: "New Hampshire" },
        { id: "NJ", text: "New Jersey" },
        { id: "NM", text: "New Mexico" },
        { id: "NY", text: "New York" },
        { id: "NC", text: "North Carolina" },
        { id: "ND", text: "North Dakota" },
        { id: "OH", text: "Ohio" },
        { id: "OK", text: "Oklahoma" },
        { id: "OR", text: "Oregon" },
        { id: "PA", text:...