Create multiple td in a single ng-repeat - javascript

I have a problem building a table.
at the moment I have code like:
<tr ng-repeat="...">
<td>Some tds before</td>
<td ng-repeat="foo in allFoo()">
{{foo.v1}} ({{foo.v2}})
</td>
<td>Some tds after</td>
</tr>
What I really need is to build two columns in here. Somehow move that inner ng-repeat from the element an set it outside. something like:
<tr ng-repeat="...">
<td>Some tds before</td>
<foobar ng-repeat="foo in allFoo()">
<td>{{foo.v1}}</td>
<td>{{foo.v2}}</td>
</foobar>
<td>Some tds after</td>
</tr>
How do I do this?

Try this..
<tr ng-repeat="...">
<td>Some tds before</td>
<td ng-repeat-start="foo in allFoo()">{{foo.v1}}</td>
<td ng-repeat-end>{{foo.v2}}</td>
<td>Some tds after</td>
</tr>
Read more about ng-repeat-start and ng-repeat-end at https://docs.angularjs.org/api/ng/directive/ngRepeat

Use a <table> within <tr> to build two columns
<tr ng-repeat="...">
<td>Some tds before</td>
<table>
<tr>
<th>Foo V1</th>
<th>Foo v2</th>
</tr>
<tr ng-repeat="foo in allFoo()">
<td>{{ foo.v1 }}</td>
<td>{{ foo.v2 }}</td>
</tr>
</table>
<td>Some tds after</td>
</tr>

Related

Get a specific row from specific table with JavaScript?

Say my dynamic HTML looks something like this:
<table id="DanishCompanies">
<tr><th>Name</th><th>Employees</th><th>Founded</th></tr>
<tr id="19"><td>Company A</td><td>80</td><td>1980</td></tr>
<tr id="17"><td>Company B</td><td>12</td><td>1910</td></tr>
<tr id="26"><td>Company C</td><td>5000</td><td>2015</td></tr>
</table>
<table id="SwedishCompanies">
<tr><th>Name</th><th>Employees</th><th>Founded</th></tr>
<tr id="10"><td>Company D</td><td>500</td><td>1950</td></tr>
<tr id="12"><td>Company E</td><td>900</td><td>1990</td></tr>
<tr id="17"><td>Company F</td><td>90</td><td>2010</td></tr>
</table>
<table id="NorwegianCompanies">
<tr><th>Name</th><th>Employees</th><th>Founded</th></tr>
<tr id="17"><td>Company G</td><td>105</td><td>1970</td></tr>
<tr id="18"><td>Company H</td><td>100</td><td>1980</td></tr>
<tr id="19"><td>Company I</td><td>45</td><td>2000</td></tr>
</table>
Each tr has an ID, but ID only relatively unique to the table, as other tables might have the ID, and the number of rows might vary.
How would I obtain the founding year (column 2) of a Swedish company with an id of 17?
I would imagine you would do it like this but I fail to find the correct code.
var table = document.getElementById("SwedishCompanies");
var row_index = ??? //should return 2
return table[row_index].cells[2].innerHTML;
I can't use getElementById just to get id "17", because I would risk getting Danish or Norwegian's company because the order of these tables is random.
you're just not using the right selector,
#DanishCompanies tr[id="17"]
will get you the tr with id 17 that's a child of DanishCompanies :
const row = document.querySelector('#DanishCompanies tr[id="17"]');
const year = row.cells[2].innerHTML;
console.log(year);
<table id="DanishCompanies">
<tr>
<th>Name</th>
<th>Employees</th>
<th>Founded</th>
</tr>
<tr id="19">
<td>Company A</td>
<td>80</td>
<td>1980</td>
</tr>
<tr id="17">
<td>Company B</td>
<td>12</td>
<td>1910</td>
</tr>
<tr id="26">
<td>Company C</td>
<td>5000</td>
<td>2015</td>
</tr>
</table>
<table id="SwedishCompanies">
<tr>
<th>Name</th>
<th>Employees</th>
<th>Founded</th>
</tr>
<tr id="10">
<td>Company D</td>
<td>500</td>
<td>1950</td>
</tr>
<tr id="12">
<td>Company E</td>
<td>900</td>
<td>1990</td>
</tr>
<tr id="17">
<td>Company F</td>
<td>90</td>
<td>2010</td>
</tr>
</table>
<table id="NorwegianCompanies">
<tr>
<th>Name</th>
<th>Employees</th>
<th>Founded</th>
</tr>
<tr id="17">
<td>Company G</td>
<td>105</td>
<td>1970</td>
</tr>
<tr id="18">
<td>Company H</td>
<td>100</td>
<td>1980</td>
</tr>
<tr id="19">
<td>Company I</td>
<td>45</td>
<td>2000</td>
</tr>
</table>
this way (id with number values complicates the css select syntax)
function getTDval( tableId, rowId, colNum)
{
return document
.querySelector(`table#${tableId} tr[id="${rowId}"]`)
.cells[colNum].textContent
}
console.log( getTDval('SwedishCompanies','17',2) )
<table id="DanishCompanies">
<tr><th>Name</th><th>Employees</th><th>Founded</th></tr>
<tr id="19"><td>Company A</td><td>80</td><td>1980</td></tr>
<tr id="17"><td>Company B</td><td>12</td><td>1910</td></tr>
<tr id="26"><td>Company C</td><td>5000</td><td>2015</td></tr>
</table>
<table id="SwedishCompanies">
<tr><th>Name</th><th>Employees</th><th>Founded</th></tr>
<tr id="10"><td>Company D</td><td>500</td><td>1950</td></tr>
<tr id="12"><td>Company E</td><td>900</td><td>1990</td></tr>
<tr id="17"><td>Company F</td><td>90</td><td>2010</td></tr>
</table>
<table id="NorwegianCompanies">
<tr><th>Name</th><th>Employees</th><th>Founded</th></tr>
<tr id="17"><td>Company G</td><td>105</td><td>1970</td></tr>
<tr id="18"><td>Company H</td><td>100</td><td>1980</td></tr>
<tr id="19"><td>Company I</td><td>45</td><td>2000</td></tr>
</table>
It is invalid HTML to reuse the same id value within a page. You might use private data-... attributes for that.
Apart from that, the following line gets the human readable text of the third child node (third column in this case), which is the year (as a string).
document.querySelector('#DanishCompanies tr[id="17"]')
.children[2].innerText;
If you can't rely on getElmentById that means that you are doing something wrong, an id should be unique in the whole html. I suggest a new naming technique, you can concatenate the parent table id with the current row id. Example:
<table id="NorwegianCompanies">
<tr><th>Name</th><th>Employees</th><th>Founded</th></tr>
<tr id="NorwegianCompanies17"><td>Company G</td><td>105</td><td>1970</td></tr>
<tr id="NorwegianCompanies18"><td>Company H</td><td>100</td><td>1980</td></tr>
<tr id="NorwegianCompanies19"><td>Company I</td><td>45</td><td>2000</td></tr>
</table>
In that way you can simply call
const row = document.getElementById(rowId)

Cant find table-rows

I'm trying find and Delete the rows <tr> as you see in code below, but for some reason it can't find elements.
$('#ResultProduct').on('click', '.deletebtn', function(e) {
var targetElement = $(e.target);
$(targetElement).closest("tr").find('.RMAJS').remove();
$(targetElement).closest("tr").find('.section').remove();
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<table>
<tbody id="ResultProduct">
<tr>
<td><a class="deletebtn">Delete</a></td>
</tr>
<tr class="RMAJS">
<td>some text 1</td>
<td>some text 1</td>
</tr>
<tr class="section">
<td>some text 1</td>
<td>some text 1</td>
</tr>
<tr>
<td><a class="deletebtn">Delete</a></td>
</tr>
<tr class="RMAJS">
<td>some text 2</td>
<td>some text 2</td>
</tr>
<tr class="section">
<td>some text 2</td>
<td>some text 2</td>
</tr>
</tbody>
</table>
Can anyone please help me!
Using closest() then find() will go up to the tr then back down into the element using find(). You would need to find('tbody') then look inside that element to find('.RMAJS').
This wouldn't solve your issue, because you would end up removing all .RMAJS elements from the tbody when it looks like all you want to do is remove the next elements.
In your case, you're going to want to use next() rather than find().
$('#ResultProduct').on('click', '.deletebtn', function(e) {
var targetElement = $(e.target);
$(targetElement).closest("tr").next('.RMAJS').remove();
$(targetElement).closest("tr").next('.section').remove();
})
<table>
<tbody id="ResultProduct">
<tr>
<td><a class="deletebtn">Delete</a></td>
</tr>
<tr class="RMAJS">
<td>some text 1</td>
<td>some text 1</td>
</tr>
<tr class="section">
<td>some text 1</td>
<td>some text 1</td>
</tr>
<tr>
<td><a class="deletebtn">Delete</a></td>
</tr>
<tr class="RMAJS">
<td>some text 2</td>
<td>some text 2</td>
</tr>
<tr class="section">
<td>some text 2</td>
<td>some text 2</td>
</tr>
</tbody>
</table>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
function removeRow(row) {
$(row).closest("tr").remove();
}
<script src="https://code.jquery.com/jquery-3.1.0.js"></script><table>
<tbody id="ResultProduct">
<tr>
</tr>
<tr class="RMAJS">
<td>some text 1</td>
<td>some text 1</td>
<td><a onclick="removeRow(this)" class="deletebtn" href="#">Delete</a></td>
</tr>
<tr class="section">
<td>some text 1</td>
<td>some text 1</td>
<td><a onclick="removeRow(this)" class="deletebtn" href="#">Delete</a></td>
</tr>
<tr class="RMAJS">
<td>some text 2</td>
<td>some text 2</td>
<td><a onclick="removeRow(this)" class="deletebtn" href="#">Delete</a></td>
</tr>
<tr class="section">
<td>some text 2</td>
<td>some text 2</td>
<td><a onclick="removeRow(this)" class="deletebtn" href="#">Delete</a></td>
</tr>
</tbody>
</table>

Rearrange table rows in hardcoded table

I am unable to edit the HTML directly in a form and would like to move some things around. I created a very simplified version of what is going on below. So for example, if I would like to move the row with class "comments" to just below the row with class "matching" how could I do this on page load?
I tried doing something like:
$('tr.comments').closest('tr').after($('tr.matching').closest('tr'));
Here is the basic code, thank you for your help!! :)
<table>
<tbody>
<tr class="designation">
<td>Some text</td>
</tr>
<tr class="comments">
<td>More text</td>
</tr>
</tbody>
<tbody>
<tr class="levels">
<td>level 1</td>
</tr>
<tr class="amount">
<td>$500</td>
</tr>
</tbody>
<tbody>
<tr class="matching">
<td>donor</td>
</tr>
<tr class="mailing">
<td>yes</td>
</tr>
</tbody>
Try with this $('tr.matching').after($('tr.comments'));.
$('tr.matching').after($('tr.comments'));
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table>
<tbody>
<tr class="designation">
<td>Some text</td>
</tr>
<tr class="comments">
<td>More text</td>
</tr>
</tbody>
<tbody>
<tr class="levels">
<td>level 1</td>
</tr>
<tr class="amount">
<td>$500</td>
</tr>
</tbody>
<tbody>
<tr class="matching">
<td>donor</td>
</tr>
<tr class="mailing">
<td>yes</td>
</tr>
</tbody>
</table>
$(".matching").after($(".comments"));

Repeat across multiple elements (more than 2)

I know that I can use ng-repeat-start and ng-repeat-end to repeat two elements, <tr>s for example like this
<table>
<tr ng-repeat-start="item in list">
<td>Some text</td>
</tr>
<tr ng-repeat-end>
<td>More text</td>
</tr>
</table>
but how can I do the same for more than two elements? I want 3 <tr>s to be repeated for each item in list. Does Angular have other directives for this purpose or can I surround my repeated elements somehow, so as to be repeated for each item?
Example
<tr>
<td>Text</td>
</tr>
<tr>
<td>Some text</td>
</tr>
<tr>
<td>More text</td>
</tr>
Try this
<table>
<tr ng-repeat-start="item in list">
<td>{{item}}</td>
</tr>
<tr>
<td>{{item}}</td>
</tr>
<tr ng-repeat-end>
<td>{{item}}</td>
</tr>
</table>
For more reference check above link: https://docs.angularjs.org/api/ng/directive/ngRepeat
Also a more simple way to do this without making this kind of ... weird thing, is the following :
<div ng-repeat="item in list">
<tr>
<td>{{item}}</td>
</tr>
<tr>
<td>{{item}}</td>
</tr>
<tr>
<td>{{item}}</td>
</tr>
</tr>
No need to use start, end .. for this particular use case

How do I get the total of table data with a particular class? (jQuery)

Say I have the following table:
<table class="table questions">
<tr>
<td class="someClass">Some data</td>
<td class="someOtherclass">Some data</td>
</tr>
<tr>
<td class="someOtherClass">Some data</td>
<td class="someOtherclass">Some data</td>
</tr>
<tr>
<td class="someOtherClass">Some data</td>
<td class="someClass">Some data</td>
</tr>
</table>
How would I get the total of table data where they had the class value of someClass? e.g. for this table the total would be two.
Just use .length to find out how many there are
$('.questions .someClass').length // will return 2 since there are 2 rows
Assuming that you want to count the number for elements within a table with .someClass
$('.someClass', '.questions').length
or
$('.questions').find('.someClass').length //faster

Categories

Resources