I want to generate dynamic table with dynamic table header and row/columns according to json object comes from webapi.
Here are examples of json object whic
You can do this by using an ng-repeat
inside another. And also, use the first line to render the headers.
Note on
ngRepeat
: For some reason,angularjs@1.4.0
previous versions sorted the keys alphabetically when usingng-repeat
bykey in object
. A simple way to fix that is upgrading toangularjs@^1.4.0
which is where they fixed it.Announce of this change by angular docs:
You need to be aware that the JavaScript specification does not define the order of keys returned for an object. (To mitigate this in Angular 1.3 the ngRepeat directive used to sort the keys alphabetically.)
Version 1.4 removed the alphabetic sorting. We now rely on the order returned by the browser when running for key in myObj. It seems that browsers generally follow the strategy of providing keys in the order in which they were defined, although there are exceptions when keys are deleted and reinstated. See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/delete#Cross-browser_issues
Ref.: Iterating over object properties
The following snippet implements this solution.
angular.module('myApp', [])
.controller('myController', function($scope) {
$scope.myArray = [
{ "CustomerName": "FORD", "Australia": 0, "China": 2, "India": 0, "South Korea": 0 },
{ "CustomerName": "ICICI PRUDENTIAL", "Australia": 0, "China": 0, "India": 5, "South Korea": 0 },
{ "CustomerName": "Kimberly Clark", "Australia": 0, "China": 0, "India": 0, "South Korea": 1 },
{ "CustomerName": "McDonalds", "Australia": 1, "China": 0, "India": 0, "South Korea": 0 },
{ "CustomerName": "Novartis", "Australia": 1, "China": 0, "India": 0, "South Korea": 0 },
{ "CustomerName": "Origin Energy", "Australia": 3, "China": 0, "India": 0, "South Korea": 0 }
];
});
angular.element(document).ready(function() {
angular.bootstrap(document, ['myApp']);
});
table {
border-collapse: collapse;
}
td,
th {
padding: 2px 4px;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>
<table ng-controller="myController" border="1">
<tr>
<th ng-repeat="(key, val) in myArray[0]">{{ key }}</th>
</tr>
<tr ng-repeat="row in myArray">
<td ng-repeat="column in row">
{{ column }}
</td>
</tr>
</table>
angular.module('myApp', [])
.controller('myController', function($scope) {
$scope.sortByColumn = 'CustomerName';
$scope.sortByReverse = false;
$scope.sortBy = function(column) {
if (column === $scope.sortByColumn) {
$scope.sortByReverse = !$scope.sortByReverse;
} else {
$scope.sortByReverse = false;
}
$scope.sortByColumn = column;
};
$scope.getSortColumn = function () {
// it has to be like this, otherwize, the `orderBy sortByColumn`
// breaks for special names like "South Korea"
return '"' + $scope.sortByColumn + '"';
};
$scope.myArray = [
{ "CustomerName": "FORD", "Australia": 0, "China": 2, "India": 0, "South Korea": 0 },
{ "CustomerName": "ICICI PRUDENTIAL", "Australia": 0, "China": 0, "India": 5, "South Korea": 0 },
{ "CustomerName": "Kimberly Clark", "Australia": 0, "China": 0, "India": 0, "South Korea": 1 },
{ "CustomerName": "McDonalds", "Australia": 1, "China": 0, "India": 0, "South Korea": 0 },
{ "CustomerName": "Novartis", "Australia": 1, "China": 0, "India": 0, "South Korea": 0 },
{ "CustomerName": "Origin Energy", "Australia": 3, "China": 0, "India": 0, "South Korea": 0 }
];
});
angular.element(document).ready(function() {
angular.bootstrap(document, ['myApp']);
});
table {
border-collapse: collapse;
}
td,
th {
padding: 2px 4px;
}
[ng-click] {
cursor: pointer;
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.js"></script>
<table ng-controller="myController" border="1">
<tr>
<th ng-repeat="(key, val) in myArray[0]" ng-click="sortBy(key)">
{{ key }}
<span ng-if="sortByColumn === key">{{ sortByReverse ? '▲' : '▼' }}</span>
</th>
</tr>
<tr ng-repeat="row in myArray | orderBy : getSortColumn() : sortByReverse">
<td ng-repeat="column in row">
{{ column }}
</td>
</tr>
</table>
i'm using angular 1.6
Here marked columns are dynamic as well as its values. My table structures are below.
<table class="table table-bordered table-hover">
<thead>
<tr>
<th>Doctor</th>
<th>Target</th>
<th ng-repeat="brand in doctorTargets.brands">{|| brand.name ||}</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="item in doctorTargets.doctorTargets">
<td>{|| item.doctorName ||}</td>
<td>{|| item.target ||}</td>
<td ng-repeat="brand in item.brands">{||brand.target||</td>
</tr>
</tbody>
</table>
The logic is to get the header by iterating on the first object props using Object.keys
.
To get only the values from to the cells itself you can do ng-repeat
with (key, value) in some_obj
.
Here is a full example:
angular.module('app', []).
controller('ctrl', function($scope) {
$scope.data1 = [
{"Country":"Australia","Toner Quantity":8},
{"Country":"China","Toner Quantity":6},
{"Country":"India","Toner Quantity":11},
{"Country":"South Korea","Toner Quantity":1}
];
$scope.data2 = [
{"CustomerName":"FORD","Australia":0,"China":2,"India":0,"South Korea":0},
{"CustomerName":"ICICI PRUDENTIAL","Australia":0,"China":0,"India":5,"South Korea":0},
{"CustomerName":"Kimberly Clark","Australia":0,"China":0,"India":0,"South Korea":1},
{"CustomerName":"McDonalds","Australia":1,"China":0,"India":0,"South Korea":0},
{"CustomerName":"Novartis","Australia":1,"China":0,"India":0,"South Korea":0},
{"CustomerName":"Origin Energy","Australia":3,"China":0,"India":0,"South Korea":0}
];
$scope.getHeaders = function(arr) {
return Object.keys(arr[0]);
};
});
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="ctrl">
<table>
<tr>
<td ng-repeat="header in getHeaders(data1)">{{header}}</td>
</tr>
<tr ng-repeat="row in data1">
<td ng-repeat="(key, value) in row">{{value}}</td>
</tr>
</table>
<hr />
<table>
<tr>
<td ng-repeat="header in getHeaders(data2)">{{header}}</td>
</tr>
<tr ng-repeat="row in data2">
<td ng-repeat="(key, value) in row">{{value}}</td>
</tr>
</table>
</div>