Displaying Json Data from ng-repeat in multiple containers - angularjs

Hey I have a question about using ng-repeats. I'm trying to display user data from a large json file in two separate containers. When a user clicks on a row it displays the other piece of the ng-repeat in a different section. If someone could take a look at this fiddle and maybe give me a direction to go in that would be awesome. Thanks!
I'm also using ngTable for the table params, but I don't think that has much to do with the issue.
http://jsfiddle.net/cL5aE/1/
HTML:
<body>
<div ng-controller="myController">
<div class="col-md-6">
<table>
<tr ng-repeat="user in $data" ng-click="loadDetails()">
<td>{{user.name}}</td>
<td>{{user.id}}</td>
</tr>
</table>
</div>
<div class="col-md-6">
<tr ng-repeat="user in $data" ng-show="loadDetails()">
<td>{{user.foo}}</td>
<td>{{user.bar}}</td>
</tr>
</div>
</div>
</body>
Controller:
angular.module('app', ['ngTable']);
app.controller('myController', function ($scope, $http, ngTableParams) {
$http.get('http://myjson.com/data.json')
.success(function (data, status) {
$scope.tableParams = new ngTableParams({
page: 1, // show first page
count: 10, // count per page
sorting: {
CompleteDate: 'asc' // initial sorting
}
}, {
total: data.length, // length of data
getData: function ($defer, params) {
// use build-in angular filter
var orderedData = params.sorting() ? $filter('orderBy')(data, params.orderBy()) : data;
$defer.resolve(orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
});
$scope.loadDetails = function(data) {
//???
}
});

I would pass the user object as a parameter to a function and assign it a model. That way you don't need to use the ng-repeat in both sections leading to a cleaner and more readable code.
Pass the object you're displaying on the ng-repeat:
<tr ng-repeat="user in $data" ng-click="loadDetails(user)">
Function to load the object to a model property:
$scope.loadDetails = function(user) {
$scope.viewModel.selectedUser = user;
}
And finally assign the model property to the view:
<table>
<tr ng-show="viewModel.selectedUser">
<td>{{viewModel.selectedUser.foo}}</td>
<td>{{viewModel.selectedUser.bar}}</td>
</tr>
</table>
http://jsfiddle.net/jimenezjrs/5Cd32/

Related

How to pass row value to another angularjs controller when clicking anchor tag in row

Here is my scenario, I have rows of data in a table with ContractId and CustomerName values from a dataset. I made the ContractId value a link when the user clicks they would be redirected to another page with the CustomerName value from that row. Now I'm struggling how to pass that value and access that value in another controller.
So I have searched the internet and learned a lot of methods how to pass values from a controller to another like services, $stateparams, $rootscopes and the $broadcast,$emit methods. I have chosen the $broadcast method since my controllers are in a hierarchy and I just need my child controller to pass the CustomerName value to the parent controller. I have tried placing a ng-click within my anchor tag and created a save event and passed my CustomerName value but I'm getting a Error: $parse:syntax Syntax Error.
<div class="container" data-ng-controller="contractCtrl">
<div class="card" ng-controller="contractlistCtrl">
<form class="form-horizontal" name="formBank">
<div class="card-header">
<h2>Contract List</h2>
</div>
<div class="card-body card-padding">
<div class="card-body">
<div class="table-responsive">
<table ng-table="tableFilter" class="table table-striped table-vmiddle" show-filter="true">
<tr ng-repeat="contractDetails in $data">
<td data-title="'Contract No'" >
<a ng-href="#/admin/contract/first" ng-click="save({{ contractDetails.CustomerName }})">{{ contractDetails.ContractId }}</a>
</td>
<td data-title="'Customer'" >
{{ contractDetails.CustomerName }}
</td>
<td data-title="'Sales Agent'">
{{ contractDetails.SalesAgentName }}
</td>
<td data-title="'Item Type'">
{{ contractDetails.ItemTypeName}}
</td>
<td data-title="'Item Id'" >
{{ contractDetails.ItemId }}
</td>
<td data-title="'Item Name'" >
{{ contractDetails.Model }}
</td>
<td data-title="'Payment Terms'">
{{ contractDetails.TermName }}
</td>
<td data-title="'Status'" >
{{ contractDetails.Status}}
</td>
</tr>
</table>
</div>
</div>
<!--<button type="submit" class="btn btn-primary btn-sm m-t-20" ng-click="generateReport(ReportId,FromDate,ToDate)">Generate</button>-->
</div>
</form>
</div>
</div>
Here is my child controller
materialAdmin
.controller('contractlistCtrl', function ($rootScope, $scope, ngTableParams, $filter, contractService, $state, $timeout, $stateParams, $window) {
contractService.getListData().then(function (result) {
$scope.insertIntoDataTable(result);
});
$scope.insertIntoDataTable = function (resultData) {
$scope.data = (resultData !== null) ? resultData : [];
$scope.length = $scope.data.length;
//Filtering
$scope.tableFilter = new ngTableParams({
page: 1,
count: 10
}, {
total: $scope.data.length,
getData: function ($defer, params) {
var orderedData = params.filter() ? $filter('filter')($scope.data, params.filter()) : $scope.data;
var slice = orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count());
this.ContractId = slice;
this.CustomerName = slice;
this.SalesAgentName = slice;
this.ItemTypeName = slice;
this.ItemId = slice;
this.Model = slice;
this.TermName = slice;
this.Status = slice;
params.total(orderedData.length);
$defer.resolve(this.ContractId, this.CustomerName, this.SalesAgentName, this.ItemTypeName, this.ItemId, this.Model, this.TermName, this.Status);
}
})
}
$scope.save = function (data) {
$scope.$broadcast("SendDown", data);
}
})
Then I have this piece of code in my parent controller to receive the data
$scope.$on("SendDown", function (data) {
$scope.customerSelected = data;
});
All I'm trying to do is to pass a value to another controller when the anchor tag is clicked.
UPDATE
I have taken the advise of using $stateparams instead of broadcast and I got it working. I followed what was stated and added this code on another js file to set the state.
.state('contract.contract.contractlist', {
url: '/first/:customer',
templateUrl: 'views/contract_first.html',
controller: function ($stateParams) {
console.log($stateParams);
}
})
There are some syntax errors in your code. First of all here:
<tr ng-repeat="contractDetails in $data">
$data should be data.
Also, here there is no need of {{ }} inside ng-click :
ng-click="save(contractDetails.CustomerName)"
But, in general you don't need ng-click and you don't need $broadcast.
You just need to pass the value as parameter on redirection. One way to achieve that is:
ng-href="#/admin/contract/first/{{contractDetails.ContractId}}"
(It is better to send id instead of name)
And then in new state you can retrieve the value (with $stateParams if you are using ui-router).
EDIT: How to pass transition parameter without showing in url
You can use ui-sref directive (part of ui-router) to send the parameter to new state like this:
ui-sref="contract.contract.contractlist({customer: contractDetails.CustomerName})"
In state declaration remove the parameter from the url and add params field:
.state('contract.contract.contractlist', {
url: '/first',
templateUrl: 'views/contract_first.html',
params: {
customer: null
}
})
For documentation check here: https://github.com/angular-ui/ui-router

angularjs how to ng-repeat array values as column headings

How to ng-repeat the values of the below array as the column headings for my ng-table?
I am trying to display the value from $scope.cols array as the column headings of my table, in other words as the fields, and display all the rows.
here is my try:
<div ng-controller="mycontroller as projects">
<table ng-table-dynamic="projects.tableParams with projects.cols"
show-filter="true" class="table table-bordered table-striped">
<tr ng-repeat="row in $data">
<td ng-repeat="col in $columns">{{::row[col.field]}}</td>
</tr>
</table>
</div>
and here is my controller:
app.controller('mycontroller', ["$scope", "$filter", "ngTableParams", "DatabaseRef", "$firebaseArray",
function ($scope, $filter, ngTableParams, DatabaseRef, $firebaseArray) {
//show all projects
var showallprojects = DatabaseRef.ref("projects").orderByKey();
$scope.allprojectslist = $firebaseArray(showallprojects);
var data = $scope.allprojectslist;
data.$loaded().then(function(data) {
console.log(data.length); // data is loaded here
$scope.cols = Object.keys(data[0]);
console.log($scope.cols);
$scope.tableParams = new ngTableParams({
page: 1, // show first page
count: 7, // count per page
sorting: { country: "asc" },
filter : {
}
}, {
filterSwitch: true,
total: 0, //data.length, // length of data
getData: function ($defer, params) {
// use build-in angular filter
var filteredData = params.filter() ?
$filter('filter')($scope.allprojectslist, params.filter()) :
$scope.allprojectslist;
var orderedData = params.sorting() ?
$filter('orderBy')(filteredData, params.orderBy()) :
$scope.allprojectslist;
params.total($scope.allprojectslist.length);
// set total for recalc pagination
$defer.resolve(orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
});
}]);
note:
the ngtable dynamic model is taken from here and the doc is here.
EDIT
I've probably misunderstood your question, I thought the code above wasn't a copy of st-table examples.
In your scenario, if you want to display each $scope.cols value as a heading you need to ng-repeat="col in cols" and print out your current col value {{col}}.
I'm assuming your data inside the body of the table to be an array of objects, and each object to be in the form of [col] => value.
I'm updating the code sample below.
You simply need to structure better your table.
<div ng-controller="mycontroller as projects">
<table ng-table-dynamic="projects.tableParams with projects.cols"
show-filter="true" class="table table-bordered table-striped">
<thead>
<tr>
<th ng-repeat="col in cols">{{col}}</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="row in data">
<td ng-repeat="col in col">{{ row[col] || "empty"}}</td>
</tr>
</tbody>
</table>
</div>
So basically we're cycling the $columns array once for building the heading of the table; then we cycle the $data array to get an array of objects (I suppose), and each iteration is a new row; then inside of each row we cycle the $columns array again to get the col.field we're looking for, and each iteration will be a new <td> inside our row.
Hope this helps.

Why doesnt ngTable accept my dataset?

I have a simple piece of data that I'm trying to test with Ng-Table. I followed the example on ng-table but I'm assuming dataset is expecting a promise instead of an array. The only difference Im seeing is how Im handling $scope.
My example works if I put the data variable on scope and dont pass it to tableParams from my js file but then I lose the functionality of filters.
Ng-Table example:
https://github.com/esvit/ng-table/blob/master/examples-old/demo15.html
My Code
HTML
<div ng-app="Pulse">
<div ng-controller="MainController as main">
<table ng-table="main.groupTable" class="table" show-filter="true">
<tr ng-repeat="user in $data"
<td title="'Name'" filter="{ name: 'text'}" sortable="'name'">
{{user.name}}</td>
</tr>
</table>
</div>
Js
var app = angular.module("Pulse", ['ngTable'])
.controller("MainController", MainController );
function MainController ($scope, NgTableParams) {
var self = this;
var data = [{name: "Moroni", age: 50}];
$scope.groupTable = new NgTableParams({}, { dataset: data});
};
Currently, ng-table use 'data' property instead of 'dataset'. I guess they've just forgot to update the documentation. So just write:
$scope.groupTable = new NgTableParams({}, { data: data});
and it should work.
New version(1.x) is using 'dataset' property but the old version(0.8.3 tested) is using 'data' property

bootstrap-table not rendering upon updating model in Angular

Hi I am not able to render table using bootstrap-table and angular. here is my code, I think I need to call bootstrap-table init method in angular ajax call. Can some one guide me on how to do this..?
angular
.module('reports')
.controller(
'ReportCtrl',
[
'$scope',
'$http',
'ngProgress',
function($scope, $http, ngProgress) {
var vm = this;
vm.mdp = {};
vm.mdp.data = [];
vm.mdp.columns = [];
$scope.submit = function() {
var report = $scope.tab;
$http.post('/reports/cmd/getData', {
report : report,
date : createdAfter
}).success(function(data) {
vm.mdp.data = data;
$.each(data[0], function(key, value){
vm.mdp.columns.push(key);
});
}).error(function(error) {
alert(error);
});
};
} ]);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.15/angular.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="mdp" class="panel" ng-controller="ReportCtrl as report" ng-show="panel.isSelected('mdp')">
<table data-toggle="table" data-show-columns="true" data-search="true" data-show-export="true" data-pagination="true" data-height="299">
<thead>
<tr>
<th ng-repeat="c in report.mdp.columns" data-field= {{c}} >{{ c }}</th>
</tr>
</thead>
<tr ng-repeat="r in report.mdp.data">
<td ng-repeat="c in report.mdp.columns">{{ r[c] }}</td>
</tr>
</table>
</div>
Integrating Bootstrap Table with Angular is solved here:
https://github.com/wenzhixin/bootstrap-table/issues/165
https://github.com/AkramKamal/bootstrap-table-examples/tree/master/integrate
I have some minor changes in my implementation of this solution which I will upload to Github / JSFiddle shortly. But the links above will allow you to get going.

ng-table pagination, sorting and filter not working

I am trying to use ngTable but its not working as expected.
I've implemented pagination, sorting and filter
Here is a plunker i have created.
I have done same way as specified in the docs examples. The pagination, sorting and filter are not working.
I tried to debug but i am not getting any error messages also
I'm using a later version of ng-table but was having similar problems. Apparently you need to add show-filter="true" to the table tag. I didn't see this in the documentation/examples for ng-table but found it in the source code tests.
My Angular Version : 1.2.16
My ng-Table Version : 0.8.3
also tried it with
Angular Version : 1.2.28
ng-Table Version : 0.4.3
HTML
<div class="row">
<div class="col-lg-12">
<table ng-table="tableParams" show-filter="true" class="table table-condensed table-bordered table-striped">
<tr ng-repeat="candidate in $data">
<td data-title="'First Name'" filter="{firstName : 'text'}">{{candidate.firstName}}</td>
<td data-title="'Last Name'" filter="{lastName : 'text'}">{{candidate.lastName}}</
</tr>
</table>
</div>
JS Controller
controller: function ($scope, Candidates, NgTableParams) {
var tableParams = {
count : 15
};
var tableSettings = {
};
Candidates.getCandidates().then(function (res) {
tableSettings.data = res.data._embedded.candidates;
$scope.tableParams = new NgTableParams(tableParams, tableSettings);
});
}
first inject $filter in controller
controller('DemoCtrl', function($scope, $filter, ngTableParams) {
second, you need to apply ng-repeat to $data variable like this
<tr ng-repeat="g in $data">
Update
here working plunk, with all edits above, and angular 1.2.26 and ngtable 0.3.1
Update2
you can bind $scope.tabledata if your view is needed,after data retrieving in getData function
getData: function($defer, params) {
// use build-in angular filter
filteredData = params.filter() ?
$filter('filter')(tabledata, params.filter()) :
tabledata;
var orderedData = params.sorting() ?
$filter('orderBy')(filteredData, params.orderBy()) : filteredData;
var page=orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count());
$scope.tabledata=page;
$defer.resolve(page);
}

Resources