jquery Datatables filter rows - javascript

Hi I have a DataTables DataTable object which requests json data via an ajax call. Each object inside the json data has a property called state that can be one of a number of values. Ultimately, I'd like to create several (Data)tables, one for each state without having each table request the same data via ajax again and again. For now, I haven't managed to make a single table filter out the rows with incorrect state yet and I'd like to solve this problem first.
The DataTable object defined as follows:
$(document).ready(function () {
var table = $('#example').DataTable({
data: example,
ajax: {
url: "{{ callback_url }}",
dataType: 'json',
dataSrc: '',
},
createdRow: function (row, data, index) {
},
columns: [{
data: "Type"
}, {
data: "State",
}
}]
});
});
I want to filter the data that comes from the ajax call based on a parameter (e.g. "if (row.State == 'new') {...};"). How can I do that? Does datatables have a function that can be passed to filter each row?
I really need several tables which show data from the same ajax callback but in different states (e.g. a "New" table, an "Old" table etc.). How can I do this without requesting the same json data again and again for each table rendered? Ideally I can store the ajax in a variable but with the async process I'm not sure how this will work out.

You can use one ajax and store the data, and than create each datatable.
Example:
$(document).ready(function () {
var data = null;
$.ajax(URL, {
dataType: 'json',
success: function(ajaxData){
data = ajaxData;
newData = data.filter(function(item){ return item.State == "New"});
oldData = data.filter(function(item){ return item.State == "Old"});
var newTable = $('#newTable').DataTable({
data: newData,
});
var oldTable = $('#oldTable').DataTable({
data: newData,
});
}
});
}

Related

How to insert data in function parameters in javascript?

I initialize Datatable on the page:
$("#datatable-buttons").DataTable()
The problem is that I need to form a parameters (300 lines of code) for this Datatable, so I make an object:
var myfunctions = {
parametrs: {
ajax: {
type: "POST",
data: data,
.....
},
inittable: function() {
a = $("#datatable-buttons").DataTable(this.parametrs);
}
The problem is that data has to change depending on user input. So I make a function:
var requestdata = function() {
return document.getElementById("daterange").value;
};
I change a data in parameters to this function
ajax: {
type: "POST",
data: requestdata()...
However, when page is first time initialized the function is being called and everything work excellent however when the code calls this function after user's input, it uses the parameters from initial page initialization, not asking it current (changed!!!) value.
It is using initial data because when myfunctions object is created, the parameters object is created with initial data.
var requestdata = function() {
return document.getElementById("daterange").value;
};
var myfunctions = {
parametrs: {
ajax: {
type: "POST",
data: requestdata(), // Pass this data as a function parameter
.....
},
inittable: function() {
a = $("#datatable-buttons").DataTable(this.parametrs);
}
}
Instead of saving the data, pass the data to the function call.

How to get current table id to add to ajax data when initialisation is used for multiple tables?

I have the following initialisation for multiple tables with the same class but different id attributes:
var $table = $('table.jobs');
$table.DataTable({
....
ajax: {
url: '/my-url',
dataSrc: function (json) {
return json.data
},
data: function(data) {
data.table_id = $table.attr('id');
// gives the same id for all tables
}
},
...
});
Is there a way I can identify which table is sending the ajax request? I'm trying to avoid duplicating the entire initialisation for every table.
You can try something like this:
$('.table.jobs').each(function () {
$('#'+$(this).attr('id')).dataTable({
url: '/my-url',
dataSrc: function (json) {
return json.data
},
data: function(data) {
data.table_id = $table.attr('id');
// gives the same id for all tables
}
});

Add ajax data on DataTable before send

I initialized the DataTable in a variable:
var dataTable = $("#selector").DataTable({
processing: true,
serverSide: true,
ajax: $.fn.dataTable.pipeline({
dataType: "json",
url: "/path/ajaxurl",
data: {
"fruits": "apple",
"veggies": "banana",
},
dataSrc: "data"
}),
sPaginationType: "extStyle"
});
Now, somewhere in my script I have this checkbox that when changed will add a new data on the ajax above then initialize the draw():
$(document).on("change", "#add-some-liquors", function(e) {
// some validations here
// My attempt to add this data
dataTable.data({"drinks" : "coca-cola"});
// Draw the dataTables
dataTable.clearPipeline().draw();
});
Seems that dataTable.data({"drinks" : "coca-cola"}); does not add the drinks on the POST when I checked on the backend, I only get the apple & banana which is the two default initialized data. What am I missing?
According to the API .data method is only for retrieving. Try holding data in a variable, updating that object and then using it in .ajax method.
var items = {}
ajax: $.fn.dataTable.pipeline({
dataType: "json",
url: "/path/ajaxurl",
data: items,
Declare your data as a variable and add the drinks value later.
var data = {
"fruits": "apple",
"veggies": "banana",
};
console.log(data);
//On the click event
$('#chk').on('click', function() {
if ($(this).is(':checked')) {
data['drinks'] = 'coca-cola';
} else {
//When unchecking the option, set it's value to null
data['drinks'] = null;
//Or delete the property.
//delete data['drinks'];
}
console.log(data);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="checkbox" id="chk" />
The ajax.data object can be initialized as a function. The function will be evaluated each time the data is fetched. In this example, the value of the global variable selectedDrink will be sent with the ajax request as the drinks field.
var selectedDrink = "";
var dataTable = $("#selector").DataTable({
processing: true,
serverSide: true,
ajax: $.fn.dataTable.pipeline({
dataType: "json",
url: "/path/ajaxurl",
data: function(d) {
d.fruits = "apple";
d.veggies = "banana";
d.drinks = selectedDrink;
},
dataSrc: "data"
}),
sPaginationType: "extStyle"
});
$(document).on("change", "#add-some-liquors", function(e) {
selectedDrink = "coca-cola";
// Draw the dataTables
dataTable.clearPipeline().draw();
});

Loading js-grid then filtering data

I have data being pulled from a db using php and then passed into javascript to load js-grid. I also have a dropdown populated with php containing the default value selected and stored by the user. My goal is to populate the grid with all data returned, then filter it based on the selected option in the dropdown.
I can't seem to understand how to load then filter data using js-grid.
<script type="text/javascript">var order_json = <?= $order_json ?>; var user_list = <?= $user_list['activeListId'] ?>;</script>
<script type="text/javascript" src="js/main.js"></script>
main.js
$( document ).ready(function() {
$("#jsGrid").jsGrid({
width: "100%",
height: "400px",
inserting: false,
editing: false,
sorting: true,
paging: false,
pageSize: 30,
noDataContent: "No orders found",
data: order_json,
fields: [
{ name: "OrderId", type: "number", title: "Order ID", visible: false },
{ name: "ListId", type: "number", title: "Order List ID", visible: true},
{ name: "Name", type: "text", title: "Order Name", align: "left"}
],
});
var grid = $("#jsGrid").data("JSGrid");
grid.search({ListId: user_list})
});
I have tried some different approaches and none have worked. Any help would be appreciated.
With js-grid the actual filtering of the data should be implemented by developer.
The filtering could be done on the client-side or server-side. Client-side filtering implemented in loadData method of controller. Server-side filtering is done by a server script that receives filtering parameters, and uses them to retrieve data.
Here is how your controller.loadData method could look like:
loadData: function(filter) {
var d = $.Deferred();
// server-side filtering
$.ajax({
type: "GET",
url: "/items",
data: filter,
dataType: "json"
}).done(function(result) {
// client-side filtering
result = $.grep(result, function(item) {
return item.SomeField === filter.SomeField;
});
d.resolve(result);
})
return d.promise();
}
As for data option, it's used only for static grid data.
Worth to mention that it would be better to provide data to grid with a REST-y service (of course, it can be done with PHP).
Here is the sample project showing how to use js-grid with a REST service on PHP https://github.com/tabalinas/jsgrid-php.
loadData: function (filter) {
criteria = filter;
var data = $.Deferred();
$.ajax({
type: "GET",
contentType: "application/json; charset=utf-8",
url: "/api/advertisements",
dataType: "json"
}).done(function(response){
var res = [];
if(criteria.Title !== "")
{
response.forEach(function(element) {
if(element.Title.indexOf(criteria.Title) > -1){
res.push(element);
response = res;
}
}, this);
}
else res = response;
if(criteria.Content !== "")
{
res= [];
response.forEach(function(element) {
if(element.Content.indexOf(criteria.Content) > -1)
res.push(element);
}, this);
}
else res = response;
data.resolve(res);
});
return data.promise();
},
Whenever filtering is involved the function loadData of the controller is called.
There you can implement the filtering functionality that you want.
Here is an example of a generic filter that checks if the string you 've typed in the filter row is contained in your corresponding rows, works with numbers and other types as well
loadData: function (filter) {
return $.get('your.url.here')
.then(result => result.filter(row => Object.keys(filter).every(col =>
filter[col] === undefined
|| ('' + filter[col]).trim() === ''
|| ('' + row[col]).toLowerCase().includes(('' + filter[col]).trim().toLowerCase())
)))
}
If you're not getting your data from a server you can still use the loadData function as described here: https://github.com/tabalinas/jsgrid/issues/759
If you want to invoke filtering manually you can use the search function as described in the docs: http://js-grid.com/docs/#searchfilter-promise

How to reset the data after init , Select2

I use Select2-4.0.0 I have been struggling with this problem for a whole day that to update the data.
I search every posts I can like Update select2 data without rebuilding the control, but none have them work.
What I need is really simple (a setter to data):
I have a diaglog, which had a select. Every time I open the diaglog, I will ajax for an data to keep it in a local array like:
when dialog open :
var select2List=syncToLoadTheData();//data for select2
$('#search-user-select').select2({ //here when secondly executed, the select2's data on UI does not refreshed
data:select2List,
matcher: function(params, data){
var key = params.term;
if ($.trim(key) === '') {
return data;
}
if( (matchKeyAndPinyin(key,data.text))){
return data;
}
return null;
}
}
But the problem is even though the list is changing, the select options does not change at all.Please note in my test case, every time i open the dialog, the data from server is changed:
What I had tried:
1.when init:
data: function() { return {results: select2List}; }// not work to show any data at all
2.when secondly open dialog:
$( "#search-user-select").select2('data',newdata,true);//not work to have the new data
3.when secondly open:
$("#search-user-select").select2("updateResults");//Error, does not have this method
And some other method like directly change the array's data(only one copy of the data), but none of them work.
I had the same problem before, my problem was i need to update the select2 after every ajax request with new data.
and this how i fixed my code.
EventId = $(this).attr('id');
$.ajax({
url: 'AjaxGetAllEventPerons',
type: 'POST',
dataType: 'json',
data: {id: EventId},
})
.done(function(data) {
$("#select2_job").select2({
minimumInputLength: 2,
multiple:true,
initSelection : function (element, callback) {
//var data = data;
callback(data);
},
ajax: {
url: "/AjaxGetAllPersonForEvent",
dataType: 'json',
quietMillis: 100,
data: function (term) {
return {
term: term
};
},
results: function (data) {
var myResults = [];
$.each(data, function (index, item) {
myResults.push({
'id': item.id,
'text': item.fullname
});
});
return {
results: myResults
};
}
}
});
I hope this example will help you to solve your problem

Categories