0
votes

I am new to knockout, want to use a select form control and enable some options based on the property of object in the array bind to select control.

The array of object bind to the select form control is as follows:

soldRequestBuyerType = 
[{id: 0, description: "Highest Bidder at Auction", status: "false"}
{id: 1, description: "Nominate Another Buyer", status:"true"}
{id: 2, description: "Book to Selling Agent", status:"true"}];

If the status property of the binded object is true, the option should be enable to select and if false the option should be disabled.

Please help me to provide the binding to the select control using knockout.

2

2 Answers

0
votes

You could accomplish this using a computed observable:

function ViewModel() {
    var vm = this;

    vm.soldRequestBuyerType = [
        { id: 0, description: "Highest Bidder at Auction", status: false },
        { id: 1, description: "Nominate Another Buyer", status: true },
        { id: 2, description: "Book to Selling Agent", status: true }
    ];

    vm.availableSoldRequestBuyerType = ko.pureComputed(() => {
        return vm.soldRequestBuyerType.filter((value) => value.status);
    });
}

Working fiddle: https://jsfiddle.net/thebluenile/p86La5d3/

You could actually make the status properties observable too if you wanted to, then the select menu would be automatically updated whenever these change.

0
votes

There's an example in the docs explaining how to selectively disable options in a select element.

You create a function that compares an item to your preferred status option. After rendering each option, you apply it via the disable binding.

Here's an example showing it in action:

const statusOptions = [ "all", "true", "false" ];
const statusFilter = ko.observable("true");

const optionsData =  [
  {id: 0, description: "Highest Bidder at Auction", status: "false"},
  {id: 1, description: "Nominate Another Buyer", status:"true"},
  {id: 2, description: "Book to Selling Agent", status:"true"}
];

const setOptionDisable = function(option, item) {
  ko.applyBindingsToNode(option, { 
    disable: ko.pureComputed(
      () => statusFilter() !== "all" && item.status !== statusFilter() 
    )
  }, item);
};

ko.applyBindings({ 
  statusOptions, statusFilter, optionsData, setOptionDisable
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.2/knockout-min.js"></script>
<div>
  Show :<select data-bind="options: statusOptions, value: statusFilter">
  </select>
</div>

<select size=3 data-bind="
    options: optionsData,
    optionsText: 'description',
    optionsAfterRender: setOptionDisable">
</select>

Another approach might be to add the disabled property directly in your data, and use a foreach binding to render you options "manually" (i.e. not using the options binding).