最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Zebra stripes ignoring hidden elements - Stack Overflow

programmeradmin4浏览0评论

Say I have a table whose rows can be dynamically assigned .hidden classes. Rows with that class are hidden via CSS. The rows are also styled with alternating colours, like so:

tr:nth-child(even) {
    background-color: $light-grey;
}

However, I want every even, unhidden row to be shaded. So hidden rows are not counted when :nth-child(even) is applied, and the pattern appears consistent. The following is my immediate attempt, but it doesn't do what I'm hoping for.

tr:not(.hidden):nth-child(even) {
    background-color: $light-grey;
}

:nth-child() is simply referring to the rows' original indices, not the current selection scope from tr:not(.hidden). The two are simply 'filtered through' on top of one another.

Is there a :nth-of-scope/selection() (or simply :nth()) meta class in CSS? Are there any equivalents or alternate methods?

Or must I resort to Javascript?

(I should say that I can also use jQuery)

Say I have a table whose rows can be dynamically assigned .hidden classes. Rows with that class are hidden via CSS. The rows are also styled with alternating colours, like so:

tr:nth-child(even) {
    background-color: $light-grey;
}

However, I want every even, unhidden row to be shaded. So hidden rows are not counted when :nth-child(even) is applied, and the pattern appears consistent. The following is my immediate attempt, but it doesn't do what I'm hoping for.

tr:not(.hidden):nth-child(even) {
    background-color: $light-grey;
}

:nth-child() is simply referring to the rows' original indices, not the current selection scope from tr:not(.hidden). The two are simply 'filtered through' on top of one another.

Is there a :nth-of-scope/selection() (or simply :nth()) meta class in CSS? Are there any equivalents or alternate methods?

Or must I resort to Javascript?

(I should say that I can also use jQuery)

Share edited Nov 7, 2014 at 3:46 Jollywatt asked Nov 7, 2014 at 0:18 JollywattJollywatt 1,3652 gold badges12 silver badges31 bronze badges 0
Add a ment  | 

5 Answers 5

Reset to default 3

There is no way to do this in pure CSS as adding display:none or visibility:none doesn't remove the elements from the DOM, which is what CSS uses.

As a result, you will need to add a little JavaScript (which runs once the page has loaded) to do this, like so

var trs = document.getElementsByTagName("tr"), // Select whichever ones you need
    count = 0; // Counter for the non-hidden ones

for(var i = 0; i < trs.length; i++) {    
    if(!trs[i].classList.contains("hidden") && (count++)%2 == 0) { // Odd ones
        trs[i].style.background = "black";
    } else if(!trs[i].classList.contains("hidden")) { // Even ones
        trs[i].style.background = "lightgrey";
    }
}

Turns out using jQuery is much simpler than any sort of CSS hack:

rows = $('table tbody tr');
rows.find('tr:visible:odd').css('background-color', '#f7f7f7');

And to specify styles for both even and odd:

rows.find('tr:visible').each(function(i) {
    if (i%2) {
        $(this).css('background', '#f7f7f7');
    } else {
        $(this).css('background', 'none');
    };
});

I know, I've answered by own question—I should have made it clear that I can use jQuery!

I just wish :visible and :even would hurry up and make it into the CSS standard.

I've just managed to solve this by just adding an extra <tr> element with display: none; set (via CSS in my case but could use a style attribute) when a block of hidden rows has an odd number of elements. This won't meet every use case, but for cases where you're using multiple rows to create expanding tables it works quite well.

Not sure this is possible with pure CSS. Using display:none; and visibility:hidden; the items still exist in the DOM and so the table background color is displayed incorrectly. You can get this to work using JQuery remove() You can see my simple example on js.fiddle here

Pure CSS (no JS) solution:

The trick is to hide a row with different tag, not class. "ul/li" tags must go. In my example I use "del" tag to hide.

.list div:nth-of-type(odd) { background: ghostwhite; }
.list del { display: none; }
<div class="list">
  <div>1</div>
  <div>2</div>
  <div>3</div>
  <del>4</del>
  <div>5</div>
  <del>6</del>
  <div>7</div>
</div>

发布评论

评论列表(0)

  1. 暂无评论