datatables rows().ids() return undefined - javascript

In my datatable I set the ID attribute for rows:
'createdRow': function (row, data, dataIndex) {
$(row).attr('id', data.json.unid);
}
Under a button I want to grab the ID's:
action: function () {
var count = table
.rows({
selected: true
})
.ids();
alert("id:s" + count)
for (i = 0; i < count.length; i++) {
alert("id:" + count[i])
}
rpcService
.setIds(count
.toArray());
}
In the alert I get for the ID "undefined".
Here is what a row looks like:
<tr id="FF97C3CFC0F5FA76C12583D1003EA028" role="row" class="odd selected">
<td class=" select-checkbox"> </td>
<td>Anne Weinstein</td>
<td>ORP B</td>
<td>Anne Weinstein</td>
<td>s41660</td>
</tr>
What am I doing wrong?

You are setting IDs on the elements in the DOM, but the .ids() method is not supposed to return those.
https://datatables.net/reference/api/rows().ids()
Important This method does not read the DOM id for the tr elements, but rather gets the row id from the row's data source (location specified by rowId).
You would need to provide the IDs upfront in your data source already, so that you can match them via the rowId option, to get what datatables considers a “row id”.

Related

How to Remove a row from Table using angular js?

I am using Angular http service to perform a DELEET operation , Its working fine , after deleting the data record I have to remove that row also from table .
Below is my code for all that
$scope.DeleteSchedule = function (recordId) {
var v =$window.confirm('Are you sure you want to delete ?');
if (v == true) {
var row = '#row' + recordId;
var table = 'table #tbl_Schedule_Delete tr ' + row;
$http({
url: '#Url.Action("DeleteSchedule", "Admin")',
method: "DELETE",
params: {
recordId: recordId
}
}).then(function mySuccess(response) {
alert('Row Deleted Successfully');
angular.element(document.querySelector(table)).remove();
//$('table #tbl_Schedule_Delete tr' + row).remove();
}, function myError(response) {
$window.alert('Warning! It failed.');
});
}
}
Refrence to jQuery remove() seems to do nothing
value of variable table will be 'table #tbl_Schedule_Delete tr #row35'
angular.element(document.querySelector(table)).remove();
I checked console log and there is no error or warning . How to do this in angular JS
Update 1 :
Below is Table Mark Up
<tr id="row34" role="row" class="odd">
<td id="delete34" class="sorting_1">
<a id="deletebtn_34" ng-click="DeleteSchedule('34')"><i class="fa fa-times fa-lg" aria-hidden="true" style="color:#e90029"></i></a>
</td>
<td>34</td>
<td>11956</td>
<td>Tota Ram</td>
<td>04-10-2017</td>
<td>02-12-2017</td>
<td>Haryana</td>
<td>Badaun</td>
<td>03-11-2017</td>
</tr>
I wouldn't delete the row using angular.element but show/hide the row with ng-if of ng-show.
<tr id="row34" role="row" class="odd" ng-show="!deleted[34]">
in combination with:
after deletion in your controller:
scope.deleted[recordId] = true;
The problem is with your selection query. The selector
table #tbl_Schedule_Delete tr #row35
actually matches the following HTML structure:
<table>
<any-element id="#tabl_Schedule_Delete">
<tr>
<any-element id="#row35"></any-element>
</tr>
</any-element>
</table>
As you can see, this doesn't match your HTML structure. This is because your selection query contains a couple of whitespaces when matching elements and ids. This causes it to look for child elements when matching the ids.
To fix it, your selector should instead look like this:
var table = 'table#tbl_Schedule_Delete tr' + row;
// Notice the lack of whitespaces after 'table' and 'tr'
Side note: using document.querySelector() inside angular.element() is redundant. You could simply use angular.element(table) since, angular.element is equivalant to using $(selector) (it's actually exactly the same, in case that you have jquery loaded)

Iterate through selected rows in Datatables

I'm using Datatables and mark ids of my table with
<tr data-id='1'>
tags. I want to get the ids of selected rows. I tried this but it doesn't seem to work:
var $issueID = $(my_table.rows('.selected').nodes()).data('id');
$.each($issueID, function (value, index ) {
alert(value);
});
If I want to do it for a single row it works fine if I use
row().node()
but I can't get it right for many rows.
This should do the trick:
var selectedIds = [];
var my_table = $('#my_table').DataTable();
my_table.rows('.selected').every( function() {
selectedIds.push(this.data().id);
});
As Mike mentioned in a comment, notice that a capital D which is used to initialise the DataTable here. $().DataTable() returns a DataTables API instance, while $().dataTable() will also initialise a DataTable, but returns a jQuery object.
While searching for the same answer I came across this article. I modified the code in your question to find a working solution.
var inactiveRecord = $(my_table.rows('.selected').nodes());
$.each(inactiveRecord, function (idx, value) {
alert($(value).data('id'));
});
You should use a Class to do this in addition to your data-id.
JQUERY
$('.row').each( function() {
var value = $(this).attr('data-id');
alert(value);
})
HTML
<tr class="row" data-id="1">
<td></td>
</tr>
<tr class="row" data-id="2">
<td></td>
</tr>
<tr class="row" data-id="3">
<td></td>
</tr>
or without a Class you could just use
$('tr').each( function() {
var value = $(this).attr('data-id');
alert(value);
})
I recommend adding a class to tr so you don't accidentally get it mixed up with other rows that may not need to be counted.

Set td value based on another td name from ajax

I have the following table structre:
<tr>
<td class="name">
Stock1
</td>
<td class="price">
</td>
</tr>
<tr>
<td class="name">
Stock2
</td>
<td class="price">
</td>
</tr>
Based on the names Stock1 and Stock2, I need to set the corresponding price in the next td. I am web scraping the price thru ajax and trying to set the value as follows:
For Stock1:
$(document).ready(function() {
$.ajax({
*everything else working fine*
success: function(data) {
if($('.name').html().indexOf("Stock1") != -1) {
$(this).closest('tr').find('.price').html(data);
}
}
});
});
In this scenario, this is not working, which I'm expecting to be the td tag with class name where value is Stock1. If I replace this with ".name", the code works only if there's one name td. When I have two td tags with the class name, it doesn't work.
I need to get this done as soon as the document loads, and not on some event like mouse click or hover.
this doesn't refers to td.name element nor table.
The :contains() Selector selects all elements that contain the specified text to target the td and then use can use DOM relationship to target immediate following sibling td using .next().
$('td.name:contains("Stock1")').next('.price').html(data);
or
$('td.name:contains("Stock1")').closest('tr').find('.price').html(data);
You can also use .filter()
var var1 = 'Stock1';
$('td.name').filter(function(){
return this.textContent.indexOf(var1) != -1;
}).closest('tr').find('.price').html(data);
As per comment, now you are returning an array. So need to iterate the data object and target the desired element.
var data = [{
name: "Stock1",
price: "$12"
}, {
name: "Stock2",
price: "$15"
}]
$.each(data, function(_, d){
$('td.name').filter(function() {
return this.textContent.indexOf(d.name) != -1;
}).closest('tr').find('.price').html(d.price);
})
DEMO
Use the below code in success method, assuming the data would be in the format mentioned below.
success:function(data)
// Assigning dummy values for assumption
var data = [{
stockName: "Stock1",
price: "$12"
}, {
stockName: "Stock2",
price: "$15"
}]
// Iterating throw all td which has name [class] elements
$(".name").each(function(i, obj) {
// Dummy Validation as per the mock data to repalce the data as per the stockName
if ($(this).closest('tr').find('.name').text().trim() === data[i].stockName){
$(this).closest('tr').find('.price').html(data[i].price);
}
})
});
FIDDLE
success: function(data) {
$('.name').each(function(index, element) {
if ($(element).html().indexOf("Stock1") != -1) {
$(element).closest('tr').find('.price').html(data);
}
}
}
The current implementation may not work correctly if you have multiple Stocks are present on your page. So i will suggest you to modify your server side code a bit to return back node name (like Stock1) as well as its price. So that your ajax success data will have 2 components; like data.name and data.price. first one will get used to target DOM td and later one will be used to set the price text as follows:
For Stock1:
$(document).ready(function(){
$.ajax({
url: "someBaseURL?name=Stock1"
success: function(data) {
var name = data.name; //grab the stock name
var price = data.price; //grab the stock price
//iterate over all the names and target the one associated
$('.name').each(function(){
if($.trim($(this).text()).indexOf(name) != -1)
$(this).closest('tr').find('.price').html(price);
});
}
});
});

Retrieve data attribute of a selector class as an array

I am running a PHP + JQuery + DataTables page. Everything went fine and I have a similar mark up from the following:
.......
<tbody>
<tr data='1'>
....
</tr>
<tr data='2'>
....
</tr>
<tr data='1'>
....
</tr>
<tr data='8'>
....
</tr>
<tr data='2'>
....
</tr>
<tr data='7'>
....
</tr>
<tr data='7'>
....
</tr>
.
.
.
</tbody>
I need to get all the data attribute of all the tr in an array, well in the case of the above table, its:
var data_values = [1, 2, 8, 7];
I think that the logic may somewhat starts with $('tr').attr('data') but it returns undefined. I've performed already a query to the database and it also returns an array:
var database_returned_values = [2, 8];
My goal from the start is to remove the tr elements that are not found in the database_returned_values array. My solution is to subtract database_returned_values array from data_values. The difference will be the trs to remove. But I cannot even start to fetch data_values. How can I retrieve the data attributes of all tr and put it in an array or are there any easier way to do this?
In this case, the trs to remove are those which have data attribute of [1, 7];
You can use each() to iterate all the tr:
var data = new Array();
$("table tbody tr").each(function(){
if($.inArray($(this).attr("data")) == -1) // check if not in array
data.push($(this).attr("data"))
})
The data property needs to have something after it.
<tr data-id='7'>
And then jQuery has a nice method you can use called data.
$("tr").data("id")
You can get all the trs, then iterate them. Then, you have to read the data-* attribute (you should'n use only data="anything") and add to an empty array. Then, remove duplicates.
As long as you are using jQuery, you can do this with:
<table>
<tr data-id="1"></tr>
<tr data-id="3"></tr>
<tr data-id="1"></tr>
<tr data-id="4"></tr>
<tr data-id="4"></tr>
<tr data-id="7"></tr>
</table>
var ids = [];
$("table tr").each(function(index, item) {
ids.push($(item).data("id"));
})
alert($.unique(ids));
Fiddle: http://jsfiddle.net/chrisbenseler/s8pytwdz/
Then, iterate this new array ($.unique(ids)) and check whatever you need to check.

How to select a row from dynamic table on mouseclick event

How can get a row's value on mouse click or checking the checkbox preferably from the below given html table?
Here is the js for getting values for my table from a xml using spry
var ds1 = new Spry.Data.XMLDataSet("xml/data.xml", "rows/row");
var pv1 = new Spry.Data.PagedView( ds1 ,{ pageSize: 10 , forceFullPages:true, useZeroBasedIndexes:true});
var pvInfo = pv1.getPagingInfo();
Here is the Div with spry region containing the table that gets populated from pv1 (see js part)
<div id="configDiv" name="config" style="width:100%;" spry:region="pv1">
<div spry:state="loading">Loading - Please stand by...</div>
<div spry:state="error">Oh crap, something went wrong!</div>
<div spry:state="ready">
<table id="tableDg" onclick="runEffect('Highlight', 'trEven', {duration: 1000, from: '#000000', to: '#805600', restoreColor: '#805600', toggle:true}, 'Flashes a color as the background of an HTML element.')"
style="border:#2F5882 1px solid;width:100%;" cellspacing="1" cellpadding="1">
<thead>
<tr id="trHead" style="color :#FFFFFF;background-color: #8EA4BB">
<th width="2%"><input id="chkbHead" type='checkbox' /></th>
<th width="10%" align="center" spry:sort="name"><b>Name</b></th>
<th width="22%" align="center" spry:sort="email"><b>Email</b></th>
</tr>
</thead>
<tbody spry:repeat="pv1">
<tr class="trOdd"
spry:if="({ds_RowNumber} % 2) != 0" onclick="ds1.setCurrentRow('{ds_RowID}');"
style="color :#2F5882;background-color: #FFFFFF">
<td><input type="checkbox" id="chkbTest" class = "chkbCsm"></input></td>
<td width="10%" align="center"> {name}</td>
<td width="22%" align="center"> {email}</td>
</tr>
<tr class="trEven" name="trEven" id="trEven"
spry:if="({ds_RowNumber} % 2) == 0" onclick="ds1.setCurrentRow('{ds_RowID}');"
style="color :#2F5882;background-color: #EDF1F5;">
<td><input type="checkbox" class = "chkbCsm"></input></td>
<td id="tdname" width="10%" align="center"> {name}</td>
<td width="22%" align="center"> {email}</td>
</tr>
</tbody>
</table>
</div>
</div>
I am trying the below code but still I am not getting the alert and hence none of the answers are also not working. I know the syntax n all are everything correct, but i am not able to figure out what is the problem here!
//inside $(document).ready(function()
$("#chkbHead").click(function() {
alert("Hi");
});
My page has other tables too for aligning some contents. So when I use the below code it works perfectly on those tables except the one in the question. It might be the problem because there are only 2 tr in the table which gets populated by a spry dataset and hence not getting identified properly. May be, I am not sure, just trying to help improve my understanding
$('tr').click(function() {
alert("by");
});
The values of a Row you will get with:
$('#tableDg tbody tr').live( 'click', function (event) {
$(this).find('td').each( function( index, item ) {
if ( $(this).has(':checkbox') ) {
alert( $(this).find(':checkbox').val() );
} else {
alert( $(this).text() );
}
};
});
What exactly do you mean by value of a table row? You can get the inner html of a table row like this:
var html = '';
$('tr').click(function() {
html = $(this).html();
});
You can get attributes of the table row (e.g. it's Id) like so:
var id = '';
$('tr').click(function() {
id = $(this).attr('id');
});
Alternatively you can get the value of nested elements such as a text input like so:
var text = '';
$('tr').click(function() {
text = $(this).find('#myTextBox').val();
});
EDIT
This is how to change the checked attribute of a checkbox nested in a table row:
$('tr').click(function() {
$(this).find('input:checkbox').attr('checked', 'checked');
// alternatively make it unchecked
$(this).find('input:checkbox').attr('checked', '');
});
EDIT
As the table rows are being loaded dynamically - the $().click() event binding method will not work, because when you are calling it - the table rows do not exist, so the click event cannot be bound to them. Instead of using $().click use the jQuery live method:
$('tr').live('click', function() {
// do stuff
});
This binds the click event to all current table rows and all table rows that may be added in the future. See the jQuery docs here
you have to use Spry Observer,
something like this:
function funcObserver(notificationState, notifier, data) {
var rgn = Spry.Data.getRegion('configDiv');
st = rgn.getState();
if (notificationState == "onPostUpdate" && st == 'ready') {
// HERE YOU CAN USE YOUR JQUERY CODE
$('#tableDg tbody tr').click(function() {
$(this).find('input:checkbox').attr('checked', 'checked');
// alternatively make it unchecked
$(this).find('input:checkbox').attr('checked', '');
});
}
}
Spry.Data.Region.addObserver("configDiv", funcObserver);

Categories

Resources