javascript - Проблема с выпадающим списком при отслеживании



angularjs (4)

Атрибут ngOptions можно использовать для динамической генерации списка элементов для элемента с использованием массива или объекта.

ngModel следит за моделью по ссылке, а не по значению. Это важно знать при привязке выбора к модели, которая является объектом или коллекцией.

1. Если вы установите модель для объекта, который равен объекту в вашей коллекции, ngOptions не сможет установить выбор, потому что объекты не идентичны. Поэтому по умолчанию вы всегда должны ссылаться на элемент в вашей коллекции для предварительного выбора, например: $ scope.selected = $ scope.collection [3]

  1. ngOptions будет отслеживать идентичность элемента не по ссылке, а по результату отслеживания по выражению. Например, если элементы вашей коллекции имеют свойство id, вы можете отслеживать по item.id.

Например :

 $scope.items = [
  {
    "title": "1",
    "myChoice" :"",
      "choices": {
        "pizza": {
          "type": 1,
          "arg": "abc"
        },
        "burger": {
          "type": 1,
          "arg": "pqr"
        }
      }
   },
   {
    "title": "2",
     "myChoice" :"",
      "choices": {
        "pizza": {
          "type": 1,
          "arg": "abc"
        },
        "burger": {
          "type": 1,
          "arg": "pqr"
        }
      }
   }
  ];

Из вышеуказанного 2-го пункта отследить идентификацию предмета не по ссылке.

Добавьте keyName ключа в объект и отслеживайте по keyName или отслеживайте по arg, введите.

Отслеживание по аргументу или типу:

 <select ng-model="data.myChoice" 
                 ng-options="choice as choice.arg for choice in data.choices track by choice.arg">
           <option value="">Select Connection</option>
         </select>

Или добавьте keyName внутри объекта выбора

 $scope.items = $scope.items.filter(function(item){
    delete item.myChoice;
    item.choices = Object.keys(item.choices).map(function(choice){
        item.choices[choice].keyName = choice;
        return item.choices[choice];
    });
    return item;
  });

HTML-код:

<div ng-controller="MyCtrl">
   <ul>
   <div ng-repeat="data in items">
     <select ng-model="data.selected" 
             ng-options="choice as choice.keyName for choice in data.choices track by choice.keyName"
             ng-change="selection(data.selected)">
       <option value="">Select</option>
     </select>

   </div>
   </ul>
</div>

Example демонстрационной ссылки

У меня проблема при связывании моего выпадающего значения с ассоциативным массивом.

Проблема связана с отслеживанием, поэтому, когда я не добавляю отслеживание в раскрывающемся списке, у меня появляется привязка с раскрывающимся списком, и когда я добавляю отслеживающий элемент, O не может автоматически выбрать значение раскрывающегося списка.

Я хочу использовать track by с помощью ng-options, чтобы angular js не добавлял $$ hashKey и использовал преимущество в производительности, связанное с track by.

Я не понимаю, почему это происходит.

Примечание. Я хочу связать только названия вариантов, таких как пицца или бургер, для каждого из моих $ scope.items, а не для целого объекта .

Обновление: Как я понимаю, и с таким большим количеством попыток с текущей структурой данных моих $ scope.items он не работает с ng-options, и я хочу использовать ng-options с track by, чтобы избежать генерации хеш-ключа Angular JS Я также попробовал ng-change, как предложено @MarcinMalinowski, но я получаю ключ как неопределенный.

Итак, какой должна быть моя структура данных $ scope.items, чтобы при необходимости доступа к любому элементу из моего $ scope.items? Я могу получить к нему доступ без выполнения цикла (как мы получаем доступ к элементам из ассоциативного массива), например, как я могу получить доступ сейчас с правильной структурой данных и используя ngoptions только с track by.

var app = angular.module("myApp", []);
app.controller("MyController", function($scope) {
  $scope.items = [
  {
    "title": "1",
    "myChoice" :"",
      "choices": {
        "pizza": {
          "type": 1,
          "arg": "abc",
          "$$hashKey": "object:417"
        },
        "burger": {
          "type": 1,
          "arg": "pqr",
          "$$hashKey": "object:418"
        }
      }
   },
   {
    "title": "2",
     "myChoice" :"",
      "choices": {
        "pizza": {
          "type": 1,
          "arg": "abc",
          "$$hashKey": "object:417"
        },
        "burger": {
          "type": 1,
          "arg": "pqr",
          "$$hashKey": "object:418"
        }
      }
   }
  ];
   
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<ul ng-app="myApp" ng-controller="MyController">
   <div ng-repeat="data in items">
       <div>{{data.title}}
       </div>
     <select ng-model="data.myChoice" 
     ng-options="key as key for (key , value) in data.choices track by $index"><option value="">Select Connection</option></select>
   </div>
   
   </ul>


Answer #1

Вам нужно добавить ng-change и передать / использовать значение ng-model, чтобы получить любое свойство, которое вы пожелаете.


Answer #2

ngOptions не создает новую область видимости, такую ​​как директива ngRepeat каждого элемента, поэтому вам не нужно заботиться о том, чтобы избавиться от $$hashKey

Я бы использовал ng-repeat для итерации <option> (предположим, вы не создаете длинные списки):

<select ng-model="data.myChoice">    
    <option value="">Select Connection</option>
    <option ng-repeat="(key , value) in data.choices track by key" ng-value="key" title="{{key}}"
    >{{key}}</option>
</select>

Рабочая демо-скрипка

Взгляните на эту проблему: github.com/angular/angular.js/issues/6564 - отслеживайте ng-options и выбирайте как несовместимые

Я полагаю, что эта проблема все еще существует, поэтому предлагаю вам использовать ngRepeat вместо track by . Для небольшого списка нет потери производительности


Answer #3
<select class="form-control pickupaddress ng-pristine ng-valid ng-touched m-r-sm m-t-n-xs" ng-model="item.pickup_address" tabindex="0" aria-invalid="false" ng-options="add._id as add.nick_name for add in addPerFood[item.food._id] | unique:'nick_name'" ng-change="dropDownSelect(item.pickup_address,allCarts,item,$index)">




angularjs