I was wondering, whether it's possible to select <tr>
's from a <table>
where <td>
's meets multiple conditions. For example (see sample table at the end ):
Get all <tr>
's where first column is "Audi" AND second column is
"red"
I've allready find out how to filter by one collumn:
$('tr:has(td:nth-child(1):contains("Audi"))').doSomeThing();
But my problem is how to filter with an AND condition like:
$('tr:has(td:nth-child(1):contains("Audi") && td:nth-child(2):contains("red"))').doSomeThing();
I know that there is the Multiple Attribute Selector, but since i'm searching for the .text() property it's not apropriate for my problem.
My sample table:
<table id="list">
<tr>
<td>Audi</td>
<td>red</td>
</tr>
<tr>
<td>Audi</td>
<td>yellow</td>
</tr>
<tr>
<td>Audi</td>
<td>green</td>
</tr>
<tr>
<td>BMW</td>
<td>red</td>
</tr>
<tr>
<td>BMW</td>
<td>yellow</td>
</tr>
<tr>
<td>BMW</td>
<td>green</td>
</tr>
...
</table>
Thanx for your help!
Use the filter
method to narrow down your initial selection based on other conditions.
$('tr:has(td:nth-child(1):contains("Audi"))').filter(':has(td:nth-child(2):contains("red"))').doSomeThing();
If you're looking for a single selector, here is the less readable:
$('tr:has(td:nth-child(1):contains("Audi")):has(td:nth-child(2):contains("red"))').doSomeThing();
Here is a demonstration: http://jsfiddle.net/8Mnsf/2/
You could also improve readability somewhat by going for:
$('tr')
.has('td:nth-child(1):contains("Audi")')
.has('td:nth-child(2):contains("red")')
.doSomeThing();
Your best choice would be to use the filter()
method. Relying on jQuery's custom selectors (:contains
, :has
, etc.) is not the best idea in most cases, because the native querySelectorAll()
cannot be used when available, which can become a performance problem.
From the manual:
Because :has()
is a jQuery extension and not part of the CSS
specification, queries using :has()
cannot take advantage of the
performance boost provided by the native DOM querySelectorAll()
method. For better performance in modern browsers, use
$("your-pure-css-selector").has(selector/DOMElement)
instead.
Also a selector like that is hardly readable, so it reduces maintainability as well. A filter()
method is simple readable code that can be reasonably commented as well if needed.
Something like this:
$('tr').filter(function () {
var $cells = $(this).children('td');
return $cells.first().text() === 'Audi'
&& $cells.eq(1).text() === 'red';
});
jsFiddle Demo