:nth-child() 擬似クラスについて
:nth-child() 擬似クラスの仕様として、W3CのRecommendation仕様書(日本語訳)には以下のように記されています。
6.6.5.2. :nth-child() 擬似クラス
:nth-child(an+b) 擬似クラスは、文書ツリーにおいて、ある要素の子で、その前に an+b-1 個 (n は正の整数もしくは0) の兄弟を持つ状態を表す。a と b が正の数である場合、擬似クラスは要素の子を a 個ずつのグループに分け (最後のグループは余りを持つ)、それぞれのグループから b 番目の要素を選択する。この擬似クラスによりたとえば、表において行ごとを選択することや、4つの段落をひとつのグループとし、グループ内の段落それぞれに異なる色を与えることなどができる。a と b の値は整数 (正、負、もしくは0) でなければならない。最初の子要素のインデックスは1となる。
日本語訳を読んでもなんだかよくわかりません。
簡単に説明すると次のようになります。
n番目の子となるE要素にスタイルを適用する際に使用します。
:nth-child() の簡単な例
:nth-child() の簡単なサンプル
これは2番目のliに赤のボーダーをつけます。
HTMLコード
<ul> <li>aaaaa</li> <li>bbbb</li> <li>ccccc</li> </ul>
CSSコード
li:nth-child(2){ border:1px solid red; }
次のようなHTML構造だと少し戸惑います。どの文字に赤いボーダーが入るでしょうか?
簡単なサンプルで勉強した場合は、eeeeeと答えてしまいがちですが、実はcccccに赤いボーダーがつきます。
:nth-child() の間違いやすいサンプル
HTMLコード
<div> <h1>aaaaa</h1> <h2>bbbb</h2> <p>ccccc</p> <p>ddddd</p> <p>eeeee</p> </div>
CSSコード
p:nth-child(3){ border:1px solid red; }
この状態がW3Cの仕様書に書かれている次の部分にあたります。
擬似クラスは、文書ツリーにおいて、ある要素の子で、その前に an+b-1 個 (n は正の整数もしくは0) の兄弟を持つ状態を表す。
「ある要素」はdivです。その子要素が h1, h2, p にあたります。
an+b-1 個 は()の中の3です。
つまり、p:nth-child(3)のことを意味します。
最初の子要素のインデックスは1ですから、最初から3番目のp要素cccccでマッチするわけです。
もう少し詳しく書くなら「ある要素の中にいる兄弟要素の3番目の兄弟でしかもp要素のもの」この条件に合う要素がマッチすることになるのです。
兄弟間にどんな要素があっても関係ないのがnth-child()の特徴です。さらに、もし3番目にp要素がなければマッチは起こらずにボーダーは適用されません。
それでは、CSSの「p:nth-child(3)」の設定はそのままで、HTMLを以下のように変更すると赤いボーダーはどこにつくでしょうか?
サンプル
HTMLコード
<div> <h1>aaaaa</h1> <h2>bbbb</h2> <p>ccccc</p> <div> <p>ddddd</p> <p>fffffffff</p> <p>ggggggg</p> </div> <p>eeeee</p> </div>
これも上の例と同様に考えます。この場合は「ある要素の子」が外側のdivの子要素であり、入れ子状態のdiv要素にもあてはまります。
つまり入れ子状態ができるに従って「ある要素の子」は複数登場してしまうことになるのです。
このような入れ子状態の場合はp:nth-child(3)に複数マッチすることが考えられます。
結果としてはcccccとgggggggに赤いボーダーがつきます。
入れ子状態になる構造の場合はセレクターをしっかりと考えてないと予期せぬ結果が起こることになります。
全称セレクタを活用した方法
次に変わったセレクタの指定方法をみてみましょう。
疑似クラスのコロンの前に半角英数のスペースをひとつ入れています。
セレクタがdivの後に半角スペースを一つ入れてから:nth-child(3)の記述をしています。
どのような結果になるか少し考えてみてください。
サンプル
HTMLコード
<div> <h1>aaaaa</h1> <h2>bbbb</h2> <p>ccccc</p> <p>ddddd</p> <p>eeeee</p> </div>
CSSコード
div :nth-child(3){ border:1px solid red; }
そもそもこの例ではdivに兄弟要素はないし、これはボーダーが付かないと考えてしまいます。
けれども答えはサンプルのようにcccccに赤いボーダーがつきます。
さて、この挙動ですが、CSSのセレクタの設定にポイントがあります。
divと:nth-child(3)の間に半角スペースが入っています。ココの半角スペースがポイントです。
ここの半角スペースはアスタリスク(*)、つまり全称セレクタが省略されていると認識されます。
つまり「 div *:nth-child(3) 」と同等に意味になります。
そのため、div要素の子孫要素すべての要素の中で3番目の要素という解釈になるわけです。
その結果3番目の要素がどんなタグでもマッチすることになります。
サンプル
*教科書で使用している「HTML&CSS標準デザイン講座」、またその新版の本でも「nth-child()」の説明が全てこの記述になっています。おそらく独学の方にとっては混乱のもとになると思われます。半角スペースを使ったdiv :nth-child(3)の意味がきちんと説明されていませんので、誤解を生みやすくなっています。注意してください。
:nth-child(an+b)の使い方
:nth-child(an+b)のan+bを使用してみましょう。
:nth-child(n)として()の中をnとすると0から1ずつ数字が入りセレクタで指定した要素の数全てがマッチします。
サンプル
HTMLコード
<ul> <li>aaaaa</li> <li>bbbb</li> <li>ccccc</li> <li>dddd</li> <li>eeeee</li> <li>ffffffff</li> <li>ggggg</li> <li>hhhhh</li> <li>iiiiiiiiiii</li> <li>jjjjjjjjjj</li> </ul>
CSSコード
li:nth-child(n){ border:1px solid red; }
nの使い方は以上のようになります。これをうまく利用するとさまざまな要素とマッチングができます。
例えば2nとすれば2の倍数とマッチング(偶数)、3nとすれば3の倍数とマッチングします。
偶数奇数
偶数は :nth-child(2n)
偶数サンプル
奇数は :nth-child(2n+1)
奇数サンプル
で表されます。nは0か正の整数です。つまり0,1,2,3,4,5,6,・・・・となります。
偶数、奇数を指定する場合はキーワードも用意されています。
偶数は :nth-child(even)
evenサンプル
奇数は :nth-child(odd)
:nth-child(an+b)のb値を使ってみる
an+bのb値を設定するとbの値以上にマッチングします。
サンプル
HTMLコード
<ul> <li>aaaaa</li> <li>bbbb</li> <li>ccccc</li> <li>dddd</li> <li>eeeee</li> <li>ffffffff</li> <li>ggggg</li> <li>hhhhh</li> <li>iiiiiiiiiii</li> <li>jjjjjjjjjj</li> </ul>
CSSコード
li:nth-child(n+5){ border:1px solid red; }
-an+bとして-aの値を設定するとbの値以下にマッチングします。
:nth-child(-an+b)
サンプル
li:nth-child(-n+5){ border:1px solid red; }
コメントを投稿するにはログインしてください。