Search code examples
javascriptangularjsangularjs-ng-repeatangularjs-ng-model

angular select ng-selected not working (with <option ng-repeat>)


I've spent an hour and tried every conceivable permutation of properties to bind a select to a model as object, and ng-selected does nothing.

<select ng-model="localModel.priceType">
    <option 
            ng-repeat="item in vm.priceTypes"
            ng-selected="localModel.priceType == item"
            ng-value="item"
            >{{item.name}}</option>
</select>

or

<select ng-model="localModel.priceType">
    <option 
            ng-repeat="item in vm.priceTypes"
            ng-selected="localModel.priceType.id == item.id"
            ng-value="item"
            >{{item.name}}</option>
</select>

or

<select ng-model="localModel.priceType">
    <option 
            ng-repeat="item in vm.priceTypes track by item.name"
            ng-selected="localModel.priceType.name == item.name"
            ng-value="item"
            >{{item.name}}</option>
</select>

The select list renders correctly, option values look funky i.e "object:875". and selected does not work.

I need ng-model to be the object, not object.someId.

solved this by using ng-options instead of <option> ng-repat

<select ng-model="localModel.priceType" ng-options="item as item.namefor item in vm.priceTypes track by item.name"></select>

Solution

  • ngValue expects a string for the ngValue. To use ngRepeat with the <option> tag, then use value="{{item}}" instead of ng-value. Expand the snippet below to see it working.

    angular.module('myApp', [])
      .controller('ctrl', function($scope) {
        $scope.vm = {
          priceTypes: [{
              id: 3,
              name: 'pound'
            },
            {
              id: 5,
              name: 'Yen'
            },
            {
              id: 6,
              name: 'dollar'
            }
          ]
        };
        //select model value
        $scope.localModel = {
          priceType: $scope.vm.priceTypes[1]
        };
      })
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.0/angular.min.js"></script>
    <div ng-app="myApp" ng-controller="ctrl">
      <select ng-model="localModel.priceType">
      <option 
                ng-repeat="item in vm.priceTypes as item"
                ng-selected="localModel.priceType.id == item.id"
                value="{{item}}"
                >{{item.name}}</option>
    </select>
      <div>
        priceType: {{ localModel.priceType }}
      </div>
    </div>

    A simpler approach is to use ngOptions on the <select> tag, with a combination of forms:

    select as label for value in array track by expr
    

    Refer to the comprehension_expression forms in the Arguments section under Usage for more information.

    angular.module('myApp', [])
      .controller('ctrl', function($scope) {
        $scope.vm = {
          priceTypes: [{
              id: 3,
              name: 'pound'
            },
            {
              id: 5,
              name: 'Yen'
            },
            {
              id: 6,
              name: 'dollar'
            }
          ]
        };
        //select model value
        $scope.localModel = {
          priceType: $scope.vm.priceTypes[1]
        };
      })
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.0/angular.min.js"></script>
    <div ng-app="myApp" ng-controller="ctrl">
      <select ng-model="localModel.priceType" ng-options="item as item.name for item in vm.priceTypes track by item.name">
    </select>
      <div>
        priceType: {{ localModel.priceType }}
      </div>
    </div>