Ng-table access to nested fields while grouping - angularjs

I'm trying grouping by nested field, but groupBy doesn't work,it works only by primary fields.
$scope.groupby = ' ';
$scope.tableParams = new ngTableParams({
page: 1,
count: 10,
sorting: {
name: 'asc'
}
}, {
total: function () {
return $scope.alert.length;
},
groupBy: 'alertRuleCategory.name',
getData: function ($defer, params) {
var orderedData = params.sorting() ? $filter('orderBy')($scope.alert, $scope.tableParams.orderBy()) : $scope.alert;
$defer.resolve(orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
Sample of alert element
{
name: 'hello',
alertRuleCategory: {
id: 1;name: 'test'
},
id: 5
};
Can you help me, to find some workaround?

Use a function for groupBy. Passing your alert object into the groupBy function allows you to access its deep properties.
groupBy: function (alert) {
return alert.alertRuleCategory.name;
}
Plunker

Related

angularjs - ngTable - issue with dynamic filter in controller

I want to create a filter for my ngTable.
In the controller at the root (not in a function) I do :
$scope.filters = {
nomSociete: 'test'
}
then
$scope.tableParamsContacts.reload();
$scope.tableParamsContacts = new ngTableParams({
page: 1, // show first page
count: 10,
filter : $scope.filters,
sorting: {
nom:'asc',
prenom:'asc'
}
}, {
total: dataContact.length, // length of data
getData: function($defer, params) {
// use build-in angular filter
var filteredData = params.filter() ?
$filter('filter')(dataContact, params.filter()) :
data;
var orderedData = params.sorting() ?
$filter('orderBy')(filteredData, params.orderBy()) :
dataContact;
params.total(orderedData.length); // set total for recalc pagination
if(params.total() < (params.page() -1) * params.count()){
params.page(1);
}
$defer.resolve(orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
It works
But if I place
$scope.filters = {
nomSociete: 'test'
}
in a function in my controller:
vm.onClientSelect = function(affaire){
$scope.filters = {
nomSociete: 'test'
}
$scope.tableParamsContacts.reload();
}
It doesn't work, the value of the filter doesn't appear in the ng table, and the ng table gets empty.
I don't understand why.
Change the filter directly from within your ngTableParams like this:
$scope.filters = {
nomSociete: 'test'
}
$scope.tableParamsContacts.filter($scope.filters);
$scope.tableParamsContacts.reload();

Iterate through all the records in all the pages in a Angular.js Datatable ng-table

I have a ng-table (angular.js datable) implementation with 25 records per page, on the page i have a submit button on clicking which i need to iterate through all records in all the pages to find which records have been modified in this table.
below is my code with which i can only iterate through the records in the current selected page, not the rest of the pages.
$scope.tableParams = new NgTableParams(
{
page: 1,
count: 25,
},
{
total: records.length,
getData: function ($defer, params) {
$scope.data = params.sorting() ? $filter('orderBy')(records, params.orderBy()) : result;
$scope.data = params.filter() ? $filter('filter')($scope.data, params.filter()) : $scope.data;
$scope.data = $scope.data.slice((params.page() - 1) * params.count(), params.page() * params.count());
$defer.resolve($scope.data);
}
});
var skus = [];
angular.forEach($scope.tableParams.data, function (product) {
if (product.quantity > 0) {
var sku =
{
AddToCart: true,
CategoryId: product.categoryId,
PriceCharged: product.displayPrice,
Quantity: product.quantity,
SkuCode: product.skuCode
}
skus.push(sku);
}
});
Probably you could use event ngTableEventsChannel.onDatasetChanged to catch modified row and copy it to a new object.
You might also try to use ng-change on edited cell.
And remember that you have all your records in records object.

ngTable.reload() unable to refresh ng-table does not show new data second time

ngTable.reload() unable to refresh ng-table does not show new data second time
code for index.js where i'm binding ng-table data.
First time databinding working properly. second time data is not binding properly. it shows previous data.
so basiccally it is unable to bind data and unable to refresh
$http.get("GetValidationsDataForTable", { params: { "entity": entity } })
.success(function (response) {
$scope.tableValue = response;
$scope.tableParams = [];
$scope.tableParams = new ngTableParams(
{
page: 1, // show first page
count: 5 // count per page
},
{
groupBy: 'Entity',
total: $scope.tableValue.length,
getData: function ($defer, params) {
var orderedData = params.filter() ?
$filter('filter')($scope.tableValue, params.filter()) :
$scope.tableValue;
var orderedData = params.sorting() ?
$filter('orderBy')($scope.tableValue, $scope.tableParams.orderBy()) : scope.tableValue;
orderedData = params.filter ?
$filter('filter')(orderedData, params.filter()) :
orderedData;
params.total(orderedData.length);
$defer.resolve($scope.tableValue.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
$scope.tableParams.reload();
})
code for index.cshtml
<table id="tblValue" ng-table="tableParams" class="customTable" style="table-layout:fixed;max-width:100%">
<tbody ng-repeat="group in $groups">
<tr ng-hide="group.$hideRows" ng-repeat="validation in group.data" style="table-layout:fixed;">
<td data-title="'Property'" style="width:10%;text-align:left !important;overflow:hidden;">
<label id="lblProperty" ng-model="validation.Property" for="Property" ng-hide="editmode" style="width:97%;word-wrap:break-word; overflow-wrap:break-word;">{{validation.Property}}</label>
<select class="form-control" data-ng-model="validation.PropertyChoice" data-ng-options="choice.Name for choice in CurrentEntityProperties" ng-change="ChangeValidationRules(validation)" ng-show="editmode" style="width:100%; ">
<option value="" style="margin-left:25px">-Select Property-</option>
</select>
</td>
</tr>
</tbody>
</table>
why ngtable.reload() does not work and also not showing new data second time?
Solution is :
$scope.tableParams = {};
$http.get("GetValidationsDataForTable", { params: { "entity": entity } })
.success(function (response) {
$scope.tableValue = response;
$scope.tableParams = [];
$scope.tableParams = new ngTableParams(
{
page: 1, // show first page
count: 5 // count per page
},
{
groupBy: 'Entity',
total: $scope.tableValue.length,
getData: function ($defer, params) {
var orderedData = params.filter() ?
$filter('filter')($scope.tableValue, params.filter()) :
$scope.tableValue;
var orderedData = params.sorting() ?
$filter('orderBy')($scope.tableValue, $scope.tableParams.orderBy()) : scope.tableValue;
orderedData = params.filter ?
$filter('filter')(orderedData, params.filter()) :
orderedData;
params.total(orderedData.length);
$defer.resolve($scope.tableValue.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
$scope.tableParams.reload();
})
i.e before every request make table parameters blank.
Solution for this problem is make table parameters blanks before any request to the data.
$scope.GetValidationsDataForTable = function(entity) {
// $("div").removeClass("container body-content");
$scope.tab1eParams = {};
SpinStart();
$http.get("GetValidationsDataForTable", {
params: {
"entity": entity
}
}).success(function(response) {
var resultArray = response;
SpinStop();
if (!$.isArray(resu1tArray) || !resultArray.1ength) {
$scope.HideFormVa1ue();
alert("Ho record found for this selection.");
}
else {
$scope.ShowFormVa1ue();
$scope.rows = response;
$scope.groupby = 'Entity',
$scope.tab1eParams = new ngTableParams({
page: 1,
count: 50,
filter: {},
sorting: {}
},
{
groupBy: $scope.groupby,
counts: [],
total: function() {
return $scope.rows.1ength;
},
getData: function($defer, params) {
$defer.resolve($scope.rows.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
You must clone params.filter() before using your service and use params.filter().yourFilter in HTML data binding.
Like that you do not need to use reload(), the ngTable will reload automatically.
Regards.

AngularJS reloading ngTable from ng-change event

I am populating ngTable using the following which works fine:
$scope.data = ClientService.query(
{
state: $scope.currentStateId,
parentId: $scope.parentId
});
$scope.data.$promise.then(function (data) {
$scope.tableParams = new ngTableParams(
{
page: 1, // show first page
count: $scope.pageCount, // count per page
sorting: { Name: 'asc' },
filter: { Name: ''}
},
{
total: data.length,
getData: function ($defer, params) {
var orderedData = params.filter() ? $filter('filter')(data, params.filter()) : data;
orderedData = params.sorting() ? $filter('orderBy')(orderedData, params.orderBy()) : orderedData;
params.total(orderedData.length); // set total for recalc pagination
$scope.accounts = orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count());
$defer.resolve($scope.accounts);
}
});
});
I now wish to update the ngTable from an ng-change event which sets a new $scope.currentStateId as follows:
$scope.stateChange = function () {
//$state.go('root.account.clients.list', { state: $scope.currentStateId, parentId : $scope.parentId }, { reload : true })
//var sel = $scope.currentStateId;
$scope.data = ClientService.query(
{
state: $scope.currentStateId,
parentId: $scope.parentId
});
$scope.tableParams.reload();
};
The ClientService.query hits the server with the correct parameters and returns the correct data but the ngTable is not updated.
Can someone please help.
Update (correct answer)
Promises, by design, can be resolved only once. As a result, nesting new ngTableParams inside of $scope.data.$promise.then(function (data) { limits your ability to update the data at a later point.
Instead, put the callback inside of the getData function so that you can reset $scope.data with a new promise before calling $scope.tableParams.reload():
$scope.data = ClientService.query({
...
});
$scope.tableParams = new ngTableParams({
...
getData: function ($defer, params) {
$scope.data.$promise.then(function (data) {
var orderedData = params.filter() ? $filter('filter')(data, params.filter()) : data;
...
$defer.resolve($scope.accounts);
});
}
});
$scope.stateChange = function () {
$scope.data = ClientService.query({
...
});
$scope.tableParams.reload();
};
Previous Answer (incorrect)
You have a synchronous function call (your ngTable update) following an asynchronous call (the ClientService query). So, the table update executes before the data comes back.
Wrap the table update call in callback that fires once the promise is resolved:
$scope.data = ClientService.query(
{
state: $scope.currentStateId,
parentId: $scope.parentId
});
$scope.data.$promise.then(function (data) {
$scope.tableParams.reload();
};

How to insert a row via ajax with NgTable?

Ok, i´m trying to do something very simple, here is my code:
<tr data-ng-repeat="data in $data | filter:searchText">
and i´ve this function, it´s called when i want to generate my table...
$scope.init = function (obj) {
if (isValid(obj)) {
generateService.sendUrlViaPost(obj.url, obj.params).then(function (response) {
$scope.$data = response;
$scope.tableParams = new ngTableParams({
page: obj.page,
count: obj.count,
}, {
total: $scope.grid.data.length,
getData: function ($defer, params) { //$data
orderedData = params.sorting() ? $filter('orderBy')($scope.$data, params.orderBy()) : $scope.$data;
$defer.resolve(orderedData.slice((params.page() - 1) * params.count(), params.page() * params.count()));
}
});
});
Calling it at my html(it´s working fine)
data-ng-init="init({url: '/Professional/GetAll', params: false, page: 1, count: 10})"
The problem is when i call it when i submit my form and i want to reload via ajax and insert one row at my ngTable...
gridService.init({ url: '/Professional/GetAll', params: false, page: 1, count: 10});
Why my ngTable isn´t reloading? I think that the problem is with my ng-repeat because it isn´t reloading my table...

Resources