I am using jQuery and datatables. I want to add a class to the TR element of a particular row. I know how to find the row. The console.dir(row); shows the row object and that starts with a tr element. I can't get the jQuery selector to do anything though. What am I missing?
table = $('#resultTable').DataTable({
aaSorting: [],
ajax: {...},
columnDefs: [...],
createdRow: function (row, data, index) {
//
// if the second column cell is blank apply special formatting
//
if (data[1] == "") {
console.dir(row);
$('tr', row).addClass('label-warning');
}
}
});
$('tr', row) is looking for a tr element in the context of row, meaning it will search for a tr element inside the row provided as context parameter.
According to API, this should work
$(row).addClass("label-warning");
You would just have to use the createdRow
$('#data-table').DataTable( {
createdRow: function( row, data, dataIndex ) {
// Set the data-status attribute, and add a class
$( row ).find('td:eq(0)')
.attr('data-status', data.status ? 'locked' : 'unlocked')
.addClass('asset-context box');
}
} );
DataTable().row.add() situation:
If you want to add class when using row add function in Datatables, you could get the TR-DOM from node() method:
var datatable = $('#resultTable').DataTable();
var trDOM = datatable.row.add( [
"Col-1",
"Col-2"
] ).draw().node();
$( trDOM ).addClass('myClass');
To set the Id attribute on the row <tr> use:
//....
rowId: "ShipmentId",
columns: [...],
//....
To set a class name on the <tr> use this calback
createdRow: function (row, data, dataIndex) {
$(row).addClass('some-class-name');
},
ref: https://datatables.net/reference/option/createdRow
To set a class on the <td> use
"columns": [
{
data:"",
className: "my_class",
render: function (data, type, row) { return "..."; }
},
{
data:"",
className: "my_class",
render: function (data, type, row) { return "..."; }
},
//...
]
Something similar for 'columnDefs'
ref: https://datatables.net/reference/option/columns.className
Also you can add class to tr by pass through json data that you send to datatable. It's enough that every json item has DT_RowClass.
For example:
{
DT_RowAttr = new
{
attr1 = "1",
attr2 = "2"
}
DT_RowClass = "majid",
DT_RowId = "rowId"
}
In this example DT_RowId value apply to id attribute of any tr tag and DT_RowAttr value apply some custom attribute to tr tag.
Another solution:
createdRow: function (row,data) {
var stsId = data.Ise_Sts_Cost_ID;
if (stsId == 3)
$(row).addClass('table-warning');
else if (stsId == 4)
$(row).addClass('table-success');
else
$(row).addClass('table-danger');
}
Related
I would like to add a context menu to each of my DataTable rows.
I want to get the row that was clicked on and then some way to identify it (I suppose the first cell value which contains the primary key would work) and then send an AJAX request containing the PK and option clicked.
I have figured out how to get the row by using "tr" as a selector, but how can I get the 1st cell's value (which contains the primary key). This prints out all of the cells:
$(function(){
$.contextMenu({
selector: 'td',
trigger: 'right',
callback: function(key, options) {
var m = $(options.$trigger).text();
window.console && console.log(m) || alert(m);
},
items: {
"delete": {name: "Delete", icon: "delete"},
});
});
Also, is this the best way to do this? I plan to have ~10 options in the context menu that interact with the rows. I am using Django as the backend.
Always use the API when you want to interact with DT. If you have an instance
var table = $('#example').DataTable( {..} )
then retrieve the current row by passing options.$trigger which holds the <tr> node :
$.contextMenu({
selector: 'tr',
trigger: 'right',
callback: function(key, options) {
var row = table.row(options.$trigger)
switch (key) {
case 'delete' :
row.remove().draw()
break;
case ...
}
},
items: {
'delete': { name: 'Delete', icon: 'delete' },
...
}
})
but how can I get the 1st cell's value (which contains the primary
key).
row.data()[0]
demo -> http://jsfiddle.net/z2q5scgr/
Row Content Sample: (this content is loaded from a json array txt file)
<div class='debug'><a href='/DH033368-4041-SR-0910-00005-006-0-CPC-20131105-1652/debug/DH033368-4041-SR-0910-000-Stage 1B Client Review-filteredCommentsXFDF.xml' target='_blank'>[webdav]</a> : /Company Home/filteredCommentsXFDF.xml</div>
I need to either find the debug class within a DataTable row(s) or search for '/debug/' in the "href" attribute and if found hide the row.
Javascript is not my strong suite. Any help is appreciated.
What I have so far:
$("#hide").click(function() {
console.log('HIDE');
$.fn.dataTable.ext.search.push(
function(settings, data, dataIndex) {
return $(table.row(dataIndex).node()).data().search("/debug/");
}
);
table.draw();
});
$("#reset").click(function() {
console.log('RESET');
$.fn.dataTable.ext.search.pop();
table.draw();
});
Thanks
Use to$() to convert the row node to a jQuery instance. This is more easy to work with. Then simply test the <div> and the <a> href for the desired matches :
$('#hide').click(function() {
$.fn.dataTable.ext.search.push(function(settings, data, dataIndex) {
var $row = table.row(dataIndex).nodes().to$();
return $row.find('div').hasClass('debug') ||
$row.find('a').attr('href').indexOf('/debug/')>-1
})
table.draw()
})
demo -> http://jsfiddle.net/3co6Lvkx/
I just implemented a DataTable in my app, but it seems like javascript doesn't work within the DataTable.
I've attached all code below for better readability.
As you can see, the ccbtn_action="delete" bit is present, but Chrome/IE/FF doesn't seem to want to do anything when the glyphicon is clicked.
This code works perfectly when called from outside the DataTable.
What gives? Is it something to do about JavaScript not being applied to dynamically generated elements?
Thank you!
Here is the Javascript code that doesn't work:
$(document).ready(function(){
// Delete Records
$('[ccbtn_action="delete"]').on('click', function() {
var type = $(this).attr('ccbtn_value_type');
var value = $(this).attr('ccbtn_value_id');
console.log('type=' + type + '&id=' + value);
if (confirm('Are you sure you want to PERMANENTLY delete this record? There is NO TURNING BACK!')) {
$.ajax({
type: 'POST',
url: 'includes/crmcore_action.php?action=cc_delete',
data: 'type=' + type + '&id=' + value,
success:
function() {
$('#cc_pagetop_status').html("<div class='alert alert-success'><strong>Success!</strong> The record was successfully deleted.</div>");
if (type == "company")
{
window.location = "companies_list.php";
}
else
{
location.reload();
}
}
});
} else {
// Do nothing!
}
});
});
Here is the code for the DataTable:
$(document).ready(function() {
var t = $('#DataTable').DataTable({
"order": [[ 1, 'asc' ]],
ajax: {
url: 'includes/dt_ss.php?getwhat=company',
dataSrc: ''
},
columns: [
{data: null},
{"data": null,
"render": function (data, type, row)
{
return ''+data.name+'';
}
},
//{data: 'name'},
{data: 'tel'},
{
"data": "id",
"render": function ( data, type, full, meta )
{
return '<span class="glyphicon glyphicon-remove" ccbtn_action="delete" ccbtn_value_type="company" ccbtn_value_id="'+data+'" data-toggle="tooltip" data-placement="bottom" title="Click me to delete"></span>';
}
}
],
});
t.on( 'order.dt search.dt', function () {
t.column(0, {search:'applied', order:'applied'}).nodes().each( function (cell, i) {
cell.innerHTML = i+1;
} );
} ).draw();
});
Since the js looks ok, this is most probably a timing issue. You part of script that binds the events is executed before the actual elements are created.
To fix that, you can:
Make sure the script runs binding after elements creation
Use dynamic binding (like .delegate() http://api.jquery.com/delegate/)
Try delegating your event like this:
$('#DataTable').on('click', '[ccbtn_action="delete"]', function() { ...
My guess is the click event is attached before your ajax request loads the DataTable rows. You can read more here about jQuery event delegation with on(). Specifically:
Event handlers are bound only to the currently selected elements; they must exist at the time your code makes the call to .on()
Try like this, but jquery version must be 1.9+
$(document).on('click', '[ccbtn_action="delete"]', function() { // your remaining code
I'm using jQuery Datatables pluging to view some data and I have in my table two columns containing checkboxes, I've tried to export the data from the table to an XSLX file using excel and excelHtml5 and also excelFlash buttons but I get two empty columns in the file, I've also included JSZip plugin in my project but in vain. How can I get the values of these checkboxes as booleans in my file.
SOLUTION
You're using DataTables 1.10.8. Before this version (1.10.7 and earlier) there was TableTools with fnCellRender option that would help to do what you want. Since 1.10.8 TableTools extension has been replaced with Buttons extension.
With Buttons extension you may use exportOptions and tell DataTables that you want the the data used for sorting (orthogonal: 'sort'). Then you need to define render function and return appropriate data when sorting is performed (type === 'sort').
/*
* Create an array with the values of all the checkboxes in a column
*/
$.fn.dataTable.ext.order['dom-checkbox'] = function (settings, col) {
return this.api()
.column(col, { order: 'index' })
.nodes()
.map(function (td, i) {
return $('input', td).prop('checked') ? '1' : '0';
});
};
var table = $('#example1').DataTable({
dom : 'Bfrtlip',
buttons: [
{
extend: 'excel',
exportOptions: {
orthogonal: 'sort'
}
}
],
columnDefs: [{
targets:[0,5],
orderDataType: 'dom-checkbox',
render: function(data, type, row, meta){
if(type === 'sort'){
var api = new $.fn.dataTable.Api( meta.settings );
var $input = $(api.cell({ row: meta.row, column: meta.col }).node()).find('input');
data = $input.prop('checked') ? '1' : '0';
}
return data;
}
}]
});
table.buttons().container()
.appendTo( $('.col-sm-6:eq(0)', table.table().container() ) );
DEMO
See this jsFiddle for code and demonstration.
I was wondering if the rendering of the table after receiving an ajax response can be modified. This seems related to the render function described here: https://www.datatables.net/manual/orthogonal-data.
My server returns Data like
{
"name":
{
id: "123456",
value: "Tiger Nixon"
}
}
I want to add to each name cell the id of the name as data-attribute or as id for the td and want to add a .on( "click", handler ) for each cell.
Is this possible?
Thanks in advance
You can use DT_RowData or DT_RowAttr (requires DataTables 1.10.5 or higher) parameters in your returned data to assign attributes to <tr> element which you can later retrieve in click handler, see Server-side processing chapter in the manual.
Alternatively you can use render method but it may not be as effective. I assumed below that index of your name column is 0 and that you want to set data-id attribute.
var table = $('#example').DataTable({
"columnDefs": [{
"data": "name.value",
"targets": 0,
"render": function ( data, type, full, meta ) {
if(type === 'display'){
$('#example').DataTable().cell(meta.row, meta.col).nodes().to$().attr('data-id', full['name']['id']);
}
return data;
}
}]
});
You can add click event handler using the code below:
$(document).ready(function(){
var table = $('#example').DataTable({
// Define DataTables initialization options here
});
$('#example tbody').on('click', 'td', function(){
// Use table to access various API function
//
// For example:
// var data_cell = table.cell(this).data();
});
});
This is possible by using the columns.createdCell function.
The answer of Gyrocode is correct for an old DataTables version.