Программный выбор ng-опций, привязанных к объектному источнику данных

У меня есть выбор ng-options, привязанный к объекту. Установка ng-модели программно работает правильно (обновляет выбор) только при установке ее в виде строки. Если я установлю ng-модель как целое число, это не сработает. Я действительно не хочу делать это преобразование. Это единственный способ?

http://jsfiddle.net/HMjnV/1/

<div ng-controller="MyCtrl">
    <select ng-options="id as name for (id, name) in items" ng-model="selected"></select>
    <div>Selected ID: {{selected}} </div>
    <button ng-click="setSelected(1)">Set Selected to ID 1 as Integer</button>
    <button ng-click="setSelected('1')">Set Selected to ID 1 as String</button>
    <div>Programmatically setting the ng-model as string sets the dropdown but not as integer.</div>
</div>

var myApp = angular.module('myApp',[]);

function MyCtrl($scope) {
    $scope.items = {1: 'a', 2: 'b', 3:'c'};
    $scope.selected = null;

    $scope.setSelected = function(id) {
        $scope.selected = id; 
    }
}

person Josh Kim    schedule 09.05.2014    source источник


Ответы (4)


ОТРЕДАКТИРОВАНО

Вы можете попробовать использовать toString, когда вы программно устанавливаете значение модели, если вы ищете быстрое и грязное решение. Подробности о сути проблемы см. в ответе @ExpertSystems.

$scope.setSelected = function(id) {
    $scope.selected = id.toString(); 
}
person Marc Kline    schedule 09.05.2014
comment
В вашем ответе утверждалось, что вы можете использовать ngOptions для привязки только к строковым значениям, и вы ссылаетесь на документы, где говорится, что вы должны использовать ngOptions когда вы хотите, чтобы модель выбора была привязана к нестроковому значению. . Я предоставил ответ, объясняющий проблему (если бы у меня было больше информации о фактических требованиях и ограничениях OP, я бы предоставил соответствующее решение). - person gkalpak; 09.05.2014
comment
Мне нравится этот подход. Я только что сделал небольшую модификацию, чтобы установить $scope.selected = String(id); - person Josh Kim; 09.05.2014

Это странно, но вы можете заставить работать привязку между ng-options и ng-model, заставив выполнять приведение в выражении понимания:

ng-options="id*1 as name for (id, name) in items" 

Вот вилка вашей скрипки, демонстрирующая этот трюк: http://jsfiddle.net/wittwerj/HMjnV/9/

Сказав это, я предпочитаю подход Марка к преобразованию toString в контроллере.

person j.wittwer    schedule 09.05.2014
comment
... одна из многих причин любить (или ненавидеть) javascript, представленный здесь. Просто умножьте строку на 1, чтобы получить число. - person Marc Kline; 09.05.2014

Да, чтобы предварительно заполнить значение, как вы сделали, тогда определенно это должно быть string. Поскольку атрибут value в теге option принимает только String. Но да, в AngularJs вы можете давать ссылки, подобные приведенным в скрипте. . И обходным путем для вашей проблемы будет преобразование id в строку.

person Shivaraj    schedule 09.05.2014
comment
Работает для моего случая. В моем случае было достаточно сделать $scope.selectedItem[item._id] = {};. Это моя директива привязки: ng-model="selectedItem[item._id]", где item происходит от директивы привязки параметров ng-options="item.name for item in items". - person Matko; 04.06.2016

JS Объекты иметь пары "имя-значение" свойства.
value может быть любого типа, но name всегда является строкой.
Хотя вы думаете, что определяете его как число, оно автоматически преобразуется в строку. Вы никак не можете это изменить (т.е. создать объект с числовыми именами свойств).

person gkalpak    schedule 09.05.2014