Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Push rows in a table rendered with ng-repeat in angular

I want to push in an extra row inline in a table when the client clicks on the row. The data should not be prefetched, since I expect there to be at most 30 rows but where each row has associated data that would be unreasonable to fetch in one get.

My approach so far is to use ng-repeat to iterate my collection and render a table. When the client presses the row, the client expects details about the row to be shown inline as an extra row under the pressed row.

<tr ng-repeat="court in courts">            
  <td>{{court.name}}</td>
  <td>{{court.number}}</td>
  <td>{{court.nrOfPlayers}}</td>
  <td>
    <a href ng:click="toggle(court.number)">Details</a>  <!-- click toggles extra row with data loaded async -->
  </td>
</tr>
<!-- extra row here -->

I have managed to show the details beneath the table with a ng-show in a hacky way, but that is not what I want.

How do you accomplish this with angular.js? What is the angular way to do this?

Here is a fiddle with a stupid squash court example http://jsfiddle.net/HByEv/

like image 460
marko Avatar asked Mar 21 '13 11:03

marko


2 Answers

I think a possible solution could be http://jsfiddle.net/HByEv/2/.

There is also an alternative for the "No players" message commented in the fiddle if you want to also get rid of the extra <tr ng-show="..."></tr>.

Edit:

As pointed in the comments, in AngularJS 1.2+ you can now use ng-repeat-start and ng-repeat-end to solve this problem.

Jossef Harush provided a fiddle: http://jsfiddle.net/3yamebfw/

like image 86
Alexandrin Rus Avatar answered Oct 20 '22 20:10

Alexandrin Rus


One sample

var app = angular.module('test-app', []);

app.controller('MyController', function($scope, $rootScope, $timeout){

    $scope.copy = {
        p1: ['c1 p1', 'c1 p2'],
        p3: ['c3 p1', 'c3 p2', 'c3 p3', 'c3 p4', 'c3 p5']
    }

    $scope.courts = [
        {
            "number": 1,
            "name": "the best court",
            "nrOfPlayers": 2
        }, {
            "number": 2,
            "name": "the bad court",
            "nrOfPlayers": 0
        }, {
            "number": 3,
            "name": "the other court",
            "nrOfPlayers": 5
        }
    ];

    $scope.loadPlayers = function(court){
        //Implement your logic here
        //Probably using ajax
        $timeout(function(){
            $scope.players = $scope.copy['p' + court.number] || [];
        }, Math.random() * 2000);
    }

    $scope.shouDetails = function(court){
        if(court.nrOfPlayers) {
            delete $scope.players;
            $scope.loadPlayers(court);
        } else {
            $scope.players = [];
        }
    }

})

Demo: Fiddle

like image 37
Arun P Johny Avatar answered Oct 20 '22 20:10

Arun P Johny