How to convert id as order number in ng-options group by..?

229 views Asked by At

This is my code

Fiddle Link

HTML

<div ng-app ng-controller="MyCtrl">
   <input type="text" ng-model = "data.name" ><br>
   <input type="text" ng-model = "data.value" ><br>
   <input type="text" ng-model = "data.id" ><br>
   <input type="button" value="ADD" ng-click = "addIntoArr(data.name, 
       data.value, data.id)" ng-disabled= !data.name>
   <select ng-model="selectItem"  ng-options="currOption as 'order' + 
     (data.indexOf(currOption)+1) group by currOption.name for currOption
         in data"></select>
   Data : {{selectItem.name}} 
</div>

Here is my Js code

  function MyCtrl($scope) {
    $scope.data = [{
       name: "AM",
       value: "11",
       id: "2"
    }, {
       name: "PM",
       value: "12",
       id: "3"
    }, {
      name: "PM",
      value: "12",
      id: "23"
    }, {
      name: "PM",
      value: "12",
      id: "33"
    }, {
      name: "AMT",
      value: "13",
      id: "33"
    }, {
      name: "WAT",
      value: "14",
      id: "21"
   }];

  $scope.addIntoArr = function (name, value, id) {
     $scope.data.push({
        name: name,
        value: value,
        id: id
    });
  }
   $scope.selectItem = $scope.data[0];
}

Here is my array I was using label AM, PM, AWT, WAT. and each has a order (Please check fiddle link). I want each label order show with number like order1 in AM, order1, order2, order3 in PM and so on. and if I add new entry in array then recently added entry should be shown in drop down with order number and Related label shown in Data.

3

There are 3 answers

3
Mikko Viitala On BEST ANSWER

I'd suggest you include some external library like lodash and format your data into more convenient structure. Then, instead of banging your head against the wall with ng-options, you could use ng-repeat.

Consider the following:

// group existing data by object's name using lodash _.groupBy
$scope.groupedData = _.groupBy($scope.data, 'name'); 

This gives your following data structure for groupedData, so there's key and value where key is e.g. AM and value is array of objects all having same name.

imgur

Then you could have following template for your select.

<select ng-model="selectItem">
  <optgroup ng-repeat="(key, items) in groupedData" label="{{ key }}">
    <option ng-repeat="item in items" 
            value="{{ item }}" 
            ng-bind="'order' + (items.indexOf(item) + 1)"></option>
  </optgroup>    
</select>

Which gives you what you are after, no?

imgur

11
ShankarSangoli On

You cannot use $index inside ng-options. However you can get the current index by using indexOf on the data item passing the current option.

<select 
   ng-model="selectItem" 
   ng-options="currOption as 'order' + (data.indexOf(currOption)+1) group by currOption.name for currOption in data"></select>

Demo http://jsfiddle.net/6cf3h54x/3/

8
Zee On

You can't use $index with ng-options. Make use of indexOf instead. You can do something like this:

<select ng-model="selectItem" ng-options="currOption.id as 'order'+data.indexOf(currOption) group by currOption.name for currOption in data"></select>