Poor Man's nth-of-type
One of the new selector types in CSS3 is nth-child. There are four related selectors in this group (nth-child, nth-last-child, nth-of-type, nth-last-of-type) and they allow for selection of elements based on order. CSS-Tricks has a nice overview of the nth-child selector type and how to use it.
Today I'm going to focus on the nth-of-type selector. This selector is similar to nth-child except it allows us to restrict our selector to a specific element type, which is often more useful than applying the style to every element regardless of type. Let's start with a set of grey floated divs and a few orange spans.
The following selector will select every other div within #my-box and turn it blue. Unlike nth-child, nth-of-type will only select the divs and skip the spans.
#my-box div:nth-of-type(2n + 2) {
background:blue; }
Well that was easy. But don't go using this selector all over the place just yet, because a few older browsers and Internet Explorer lacks support. The typical solution for this problem is to just assign class names to every other element and select the elements that way. That's no fun though. Instead, let's try to emulate support by using a selector IE does support: the general sibling selector.
The general sibling selector is simply a tilde between two element selectors which selects the second element if it exists somewhere after the first and shares a common parent element. For example, the following selector selects any div which has a div somewhere before is within #my-box:
#my-box div ~ div {
background:blue; }
We've managed to turn the second div blue, but now every div after that also matches the general sibling selector. The solution is to select the third block using the same method, then select the fourth block, then the fifth…you see where this is going.
#my-box div~div, #my-box div~div~div~div, #my-box div~div~div~div~div~div, #my-box div~div~div~div~div~div~div~div, #my-box div~div~div~div~div~div~div~div~div~div, #my-box div~div~div~div~div~div~div~div~div~div~div~div {
background:blue; }
#my-box div, #my-box div~div~div, #my-box div~div~div~div~div, #my-box div~div~div~div~div~div~div, #my-box div~div~div~div~div~div~div~div~div, #my-box div~div~div~div~div~div~div~div~div~div~div, #my-box div~div~div~div~div~div~div~div~div~div~div~div~div {
background:#CCC; }
Blam, nth-of-type emulation! Of course, there are several downsides to this method.
- The number of matched elements can never exceed the number of selectors you've put in your CSS.
- Every selector you add will be longer than the last, which can lead to increasingly large stylesheets.
- IE6 does not support the general sibling selector (I'm not too worried about it, but it's worth noting).
For something like a table that could potentially have hundreds of rows, it doesn't really make sense to weigh down your stylesheet with increasingly lengthy selectors. However, in situations where you have a limited number of elements this method works well enough, eliminates the need for extra class names in your HTML, and probably gives you some type of bragging rights.

Comments
Post new comment