:nth-child()が、(個人的に)便利すぎた！【備忘録】

おはようございます！
今日は、CSSで、最近学んだことがあり、まとめてみようと思います！

【状況】
箱型の要素をいくつか並べていたんです。しかも複数行。最初の箱は、特にmarginの調整したくなかったのですが、各行の特定の位置にある箱のmarginは調整したい！！

いつもの私だったら、「これくらいの量だったら、1つ1つクラス当ててくかー！」って思っていました。
ただ、(なぜか?)今回は違いました。
「今後も増えてく可能性あるし、そうなったら毎回位置確認してクラス当て直しになるやん！めんどくさっ！位置指定して、各行のその位置にある要素に一括でスタイル適用することってできひんのかなー？？」
と、思ったのです！

その時、:nth-child()に出会いました。
:nth-child()の便利さに感動したので、その体験を皆さんにも共有させて頂きます！！

それでは、早速、解説していきます！

# :nth-child()とは
まず、:nth-child()とは何なのか、MDNで調べてみましょう。
<dl>
<dt>
:nth-child()
</dt>
<dd>CSSの:nth-child()擬似クラスは、兄弟要素のグループの中での位置に基づいて選択します。<br>
出典)<a href="https://developer.mozilla.org/ja/docs/Web/CSS/:nth-child">MDN :nth-child()</a></dd></dl>

まず、:nth-child()は、<strong>疑似クラス</strong>と呼ばれるものの1種であることが読み取れます。
では、疑似クラスとは何なのでしょうか？

# 疑似クラスとは

<dl>
<dt>疑似クラス</dt>
<dd>CSSの擬似クラスPseudo-classesは、セレクターに付加するキーワードであり、選択された要素に対して特定の状態を指定します。例えば :hover 擬似クラスで、ユーザーのポインターが当たったときにボタンの色を変更することができます。<br>
出典)<a href="https://developer.mozilla.org/ja/docs/Web/CSS/Pseudo-classes">MDN 疑似クラス</a></dd>
</dl>

「セレクター」は、スタイルを適用する要素を表します。h1やdivなどの要素名で記述しても良いし、クラスを当てている要素であれば、「.クラス名」でも良いですね。


【例】タイトルの中央寄せ

```html
<h1>タイトル</h1>
<h1 class="title">タイトル</h1>
```

```css
h1 {
  text-align: center;
}

.title {
  text-align: center;
}
```

「選択された特定の状態を指定します」の部分は、具体的な例を挙げて説明してくれていますね！aタグでよく使う:hoverですね！
aタグで:hoverを使うときは、要素にカーソルを重ねたときのスタイルを指定しますね！例えば、色を変えたりとか！

【例】要素の上にカーソルを重ねると文字色が赤に変わるように指定

```html
<a href="https://www.google.com/">グーグル</a>
```
```css
a:hover {
  color: red;
}
```

【カーソル乗せる前】
![スクリーンショット 2021-04-13 9.25.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/619752/53cce476-ce5e-a1cf-5f69-2b3650d72a71.png)
【カーソルを乗せた状態】※スクショしてカーソルが見えなくなっているだけです。
![スクリーンショット 2021-04-13 9.30.39.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/619752/3b7424a0-3e83-1ebc-53ca-e57314d0e4c4.png)

ちゃんと【カーソルを乗せた状態】では、文字色が赤くなっていますね！

通常のスタイル指定と違うのは...
【通常】
h1や、divなどの要素を指定するだけ。

【疑似クラス】
「ユーザーが要素にカーソルを重ねたとき」「チェックボックスにチェックが入っているとき」など、対象の要素の状態に合わせてスタイルを変化させることができる！！

固定された要素指定だけではなく、状態に合わせてスタイルが指定できるって便利ですよね！

疑似クラスがわかったところで、:nth-child()について、詳しく確認して行きましょう！

# :nth-child()の使い方
:nth-child()は疑似クラス。
疑似クラスとは、要素の状態に合わせてスタイル指定をするためのキーワード。

:nth-child()が表している状態とはどういう状態を指しているのでしょうか？
もう少し詳しい解説を見つけたので、引用してみます。
<dl>
<dd>「:nth-child()」を利用すると、同一の階層の全ての要素をカウントし、「An+B」番目の要素を適用先にすることができます。<br>
出典)エビスコム著 『HTML5 & CSS3 デザイン　現場の新標準ガイド【第2版】』(2020)p.121</dd>
</dl>
同一階層の全ての要素っていうところは、1つのポイントですね！
疑似クラスが、「要素の状態に合わせてスタイル指定する」ことがわかっているので、この文章だけでも、理解できてしまう方もいるかもしれないですね！
次のHTMLを例に詳しく見ていきましょう！

【例】

```html
<div class="boxes">
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
</div>
<div class="boxes">
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
     <h2>ボックス</h2>
     <p>これは箱だよ。</p>
  </div>
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
     <h2>ボックス</h2>
     <p>これは箱だよ。</p>
  </div>
</div>
<div class="boxes">
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
  <div class="box">
    <h2>ボックス</h2>
    <p>これは箱だよ。</p>
  </div>
</div>
```

```css
.boxes {
  display: flex;
  margin-bottom: 15px;
}

.box {
  border: 2px solid #333;
}
```
![スクリーンショット 2021-04-13 9.45.43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/619752/22c81155-9d6a-3f47-4a28-9624e7a69548.png)

【この例でやりたいこと】
各行のボックスの左にmarginをとりたい！ただし、各行の最初のボックの左にはmarginいらない...

この量だと1つ1つクラスを当てるの面倒じゃないですか？？
こういうとき、:nth-child()を使うと簡単に、指定できてしまいます。

:nth-child()が表す<strong>状態</strong>は...<strong>An+B番目にある状態</strong>
Aは、何個おきかを表します。
B、B+1、B+2...というような場合(eg: 1番目、2番目、3番目...)や、A=1になります。
↓
この例では、2番目以降にある状態の要素にスタイル指定したい。つまり、
An+B = 1n+2。1はなくて良いので、<strong>n+2</strong>となります。
:nth-child(n+2)をセレクタとして用いて、margin-leftを指定すると、【この例でやりたいこと】が達成できます。

```css
.boxes .box:nth-child(n+2) {
  margin-left: 15px;
}
```

結果は以下です。
きちんと、各行2番目以降のボックスたちの左にmarginが指定され、間隔が整いました！
親要素.boxesの範囲内にある要素の中で、最初から2番目以降にある要素全てに、スタイル指定が適用されたのです！
こんな少ない記述で、いちいちクラスを当てにいかずとも一気に指定できたら便利ですよね！！！
![スクリーンショット 2021-04-13 9.46.12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/619752/01ccb457-18e0-093e-2060-3ffe7411b846.png)

今回は、2番目以降の要素に指定したかったので、n+2となりました。ですが、「その番号の位置にある要素だけ」や、「奇数番目にある要素だけ」「偶数番目にある要素だけ」といった指定の仕方もできます。

<table>
<tr>
<th>その番号の位置にある要素</th>
<td colspan="3">B</td>
</tr>
<tr>
<th>奇数番目にある要素</th>
<td>odd</td>
<td colspan="2">2n+1</td>
</tr>
<tr>
<th>偶数番目にある要素</th>
<td>even</td>
<td>2n+2</td>
<td>2n</td>
</tr>
<tr>
<th>最初のB個</th>
<td colspan="3">-n+B</td>
</tr>
</table>
また、今回説明したのは、最初から数えた場合ですが、後ろから数えることも可能です。この場合は、:nth-last-child()を使います！
やり方は一緒。ただ、最初から数えるか後ろから数えるかの違いだけです！

# おわりに
まだまだ初心者の備忘録ですが、お読み頂きありがとうございました！
もし、間違いや、補足などございましたら、コメント頂けますと、嬉しいです！！

# 参考資料
<a href="https://developer.mozilla.org/ja/docs/Web/CSS/:nth-child">MDN :nth-child()
<a href="https://developer.mozilla.org/ja/docs/Web/CSS/Pseudo-classes">MDN 疑似クラス</a>
エビスコム著 『HTML5 & CSS3 デザイン　現場の新標準ガイド【第2版】』(2020)