Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

AngularJS ng-repeat over array of objects uniquely

I have an Object with 2 arrays:

mainObject = {
  soccer: [],
  hockey: []
}

Each of the arrays contain a different amount of objects:

sportObject = {
  soccer: [{equipment: "cleats"}, {shirt: "jersey"}, {team: "arsenal"}],
  hockey: [{equipment: "skates"}]
}

I print each object onto the page using a list, separated by "sport":

<ul ng-repeat="(sport, value) in sportObject">
  <li>{{sport}}</li> // Prints "soccer" or "hockey"

  <li ng-repeat="item in sportObject"></li> //  <-- one of my failed attempts
</ul>

I want to print each of the object info into an li under the correct sport name.

For example, there are a total of 4 objects, soccer has 3, hockey has 1.

Currently, each item gets repeated under both sports. So both sports have 4, items. How can I use ng-repeat to only print equipment that falls under the correct sport title?

The result should look like:

Soccer

  • equipment: cleats
  • shirt: jersey
  • team: arsenal

Hockey

  • equipment: skates
like image 381
bruh Avatar asked Jan 26 '17 21:01

bruh


People also ask

What can I use instead of NG-repeat?

But ng-repeat is not the right thing to use when you have large datasets as it involves heavy DOM manipulations. And you should consider using ng-repeat with pagination. You can consider using transclusion inside a custom directive, to achieve the behavior you are looking for without using ng-repeat.

What is difference between ng-repeat and Ng options?

ng-options is the directive which is designed specifically to populate the items of a dropdown list. One major advantage using ng-options for the dropdown is, it allows us to pass the selected value to be an object. Whereas, using ng-repeat the selected value can only be string.

How do you prevent duplicates in NG-repeat?

You can use unique filter while using ng-repeat . If you use track by $index then unique won't work.

Does ng-repeat create a new scope?

Each iteration of ng-repeat creates a new child scope, and that new child scope always gets a new property.


2 Answers

The following should do the trick:

<ul ng-repeat="(sport, value) in sportObject">
  <li>{{sport}}
    <ul>
      <li ng-repeat="detail in value">
        <span ng-repeat="(detailkey, detailvalue) in detail">
          {{detailkey}} - {{detailvalue}}
        </span>
      </li>
    </ul>
  </li>
</ul>

Note that you have to do 3 iterations:

  • the first over the original object
  • the second over the array objects in each of the original object values
  • the third over the objects inside the arrays

And here is a working version for you: https://plnkr.co/edit/WKNRU6U6xwGgKRq4chhT?p=preview

like image 164
GPicazo Avatar answered Oct 10 '22 11:10

GPicazo


You can use key and value within the ng-repeat directive, as shown below.

<ul ng-controller="SportController">
  <strong>Soccer</strong>
  <li ng-repeat="(key,value) in sportObject.soccer">
    {{value}}
  </li>

  <strong>Hockey</strong>
  <li ng-repeat="(key,value) in sportObject.hockey">
    {{value}}
  </li>
</ul>

Additional wireup:

var app = angular.module("sportApp", []);

app.controller("SportController", function($scope) {
    $scope.sportObject = {
    soccer: [{equipment: "cleats"}, {shirt: "jersey"}, {team: "arsenal"}],
    hockey: [{equipment: "skates"}]
  }
});

I have created a plunkr here for you to view and edit:

You can also nest the ng-repeat directive.

<ul ng-controller="SportController">
  <li ng-repeat="(sportName, sportValue) in sportObject">
    {{sportName}}
    <ul ng-repeat="(key, val) in sportValue">
      <li>{{val}}</li>
    </ul>
  </li>
</ul>
like image 29
Darren Avatar answered Oct 10 '22 13:10

Darren