LoginSignup
11
15

More than 1 year has passed since last update.

疑似要素と疑似クラスを一挙にまとめてみる

Last updated at Posted at 2022-07-20

はじめに

CSSセレクタである疑似要素と疑似クラスは有用なものが多いですが、数多く存在するため覚えきれていないという方も少なくないはずです。

今回は、この2つのセレクタについてまとめていきます。
(Experimentalな機能については除外します。)

出来るだけアルファベット順に並べていますが、クラスの意味によって順番が入れ替わっていますのでご了承ください。

疑似?擬似?

ゲシュタルト崩壊しそうな人は読み飛ばしていただいて構いません。
結論としては「疑似」にしとこって感じです

検索すると恐らく「擬似要素・擬似クラス」としているサイトが多いかもしれませんが、実はMDN Docsの中でも表記が揺れています。
意味合いもほとんど同じなようで、英語ではPseudoと表しますが、これの訳を見ても「擬似/疑似」と書いてあったりします。

では一体どちらで表記するのが正しいのでしょうか?

ざっと調べてみた感じ、「疑似」が漢語としては正しいようです。

「擬似」は恐らく日本人が作った言葉なのではないか、とのこと。

ということで本記事では「疑似」と記載します。
(実生活でも疑似を使うようにしようと思いました(小並))

疑似クラス

疑似クラスは、その要素の状態に基づいてスタイルを付与することができるものです。
CSSで記述する際は、:hoverのように、コロンを1つつけます。

構文
selector:pseudo-class {
  property: value;
}

ユーザ操作

:active

アクティブ化された要素(abutton)を指定します。
一般的にクリックボタンを押下したときにアクティブ状態となります。

リンク関連の疑似クラスである:link:hover:visitedによって上書きされるため、:link:visited:hover:activeの順(LVHA順)で記述するのが良いでしょう。

:focus

フォーカスが出来る要素をクリックまたはTabキーで選択したときに一致します。

フォーカスを持つ要素を含む要素を選択したい場合は、:focus-withinを使います

:focus-visible

要素が:focusの条件に一致しているとき、UAがフォーカスしていることを明示するべきと判断された場合に適用されます。
マウスでクリックしたときはいらないけど、キーボードのTabキーで選択したときはフォーカス表示してほしいときなどに使います。

:focus-within

その要素または子孫要素にフォーカスを持つ場合に一致します。

:hover

カーソルを要素の上にかざしたときに一致します。

タッチデバイスでの使用はしばしば問題になるため考慮が必要です。

ツリー構造

:first-child

兄弟要素の中で一番最初の要素と一致します。

:last-child

兄弟要素の中で一番最後の要素と一致します。

:only-child

兄弟要素がない要素と一致します。

:nth-child()

兄弟要素の中で指定した位置と一致します。

:nth-last-child()

兄弟要素の中で指定した位置と一致します。
後ろから前にカウントしていきます。

:nth-of-type()

兄弟要素の指定した要素の中で指定した位置と一致します。

:nth-of-type():nth-child()の違い

:nth-of-type():nth-child()には、指定の要素以外の要素をカウントするかどうかの違いがあります。
前者がカウントせず、後者はカウントします。
以下の例を見てみましょう。

<section>
  <h2>title</h2>
  <p>text content<p>
  <span>category<span>
  <span>author<span>
  <span>date<span>
</section>

このようなHTMLがあった場合、それぞれの指定は以下のように選択されます。

categoryのspanを選択
span:nth-child(3) {
  color: red;
}
dateのspanを選択
span:nth-of-type(3) {
  color: red;
}

つまり、こういうことになります。
span:nth-child(3)は単純に兄弟要素を上から数えて3番目、
span:nth-of-type(3)は兄弟要素中のspanの中で上から数えて3番目、となります。

<section>
  <h2>title</h2>
  <p>text content<p>
  <span>category<span>  <!-- span:nth-child(3) -->
  <span>author<span>
  <span>date<span>  <!-- span:nth-of-type(3) -->
</section>

:nth-last-of-type()

兄弟要素の指定した要素の中で指定した位置と一致します。
後ろから前にカウントしていきます。

:first-of-type

兄弟要素の指定した要素の最初の要素と一致します。

:last-of-type

兄弟要素の指定した要素の最後の要素と一致します。

:only-of-type

同じタグの兄弟要素がない要素と一致します。

:defined

定義されているすべての要素と一致します。

:empty

要素ノードや文字列などの子を持たない要素と一致します。

:host

Shadow DOM1のルートホスト要素と一致します。
(Web Componentsについて理解していないと十分に理解できないかもしれません。)

<custom-elem class="foo">
  <div class="foo"></div>
</custom-elem>

Shadow DOM内からルートホストを選択したいときには以下のようにします。
この場合、ルートであるcustom-elemを選択することになります。

:host {
  /* styles */
}

:host()

Shadow DOMのルートホストのうち、セレクタの引数と一致するものを選択します。

<custom-elem class="foo">
  <div class="foo"></div>
</custom-elem>
:host(.foo) {
  /* styles */
}

:is()

:matches()から:is()に変わりました

引数にセレクタリストを取り、リスト中のいずれかに当てはまる要素と一致します。

header a:hover,
main a:hover,
footer a:hover {
  opacity: 0.8;
}

/* :is()で書き換えるとこんな感じ */
:is(header, main, footer) a:hover {
  opacity: 0.8;
}

:where()

引数にセレクタリストを取り、リスト中のいずれかに当てはまる要素と一致します。

header a:hover,
main a:hover,
footer a:hover {
  opacity: 0.8;
}

/* :is()で書き換えるとこんな感じ */
:where(header, main, footer) a:hover {
  opacity: 0.8;
}

:is():where()の違い

:is()は引数内で最も詳細度の高いセレクタの詳細度になるのに対し、:where()詳細度が常に0になります。

:not()

引数に指定されたセレクタに一致しない要素を選択します。

使用する際いくつか注意点があります。

  • 入れ子にはできない
  • ルールの詳細度を上げることができる
    • #foo:not(#bar)#fooの詳細度より高くなる
  • :not(.foo)は「.fooではない要素」のため、<html><body>を含む
  • 祖先要素を除外できない
  • 複数セレクタを指定する書き方はブラウザが未対応の場合がある
    • :not(.foo):not(.bar)と書く

:root

ツリーのルート要素を選択します。
HTMLでは<html>要素を表しますが、htmlセレクタより詳細度が高くなります。

フォーム

:autofill

<input>要素がブラウザによって自動補完されたときに一致します。
そのフィールドをユーザが編集すると一致しなくなります。

多くのブラウザで:-webkit-autofillbackground-colorbackground-imagecolorに対して!importantでスタイルを定義しているため、CSSでは独自でスタイルが上書きできません。

:checked

ラジオボタン、チェックボックス、オプションボタン要素が選択された状態と一致します。

:default

以下に一致します。

  • フォームのデフォルトボタンである送信ボタン<button>
  • <input type="checkbox">
  • <input type="radio">
  • selected属性を持つ<option>

:enabled

アクティブ化したりフォーカスができる要素と一致します。
例えば、disabled属性が与えられたinput要素には一致しません。

:disabled

:enabledの逆です。

:indeterminate

未確定状態にあるフォーム要素と一致します。

  • radio要素で、同じnameの値を持つ全てのラジオボタンが未選択状態のとき
  • checkbox要素で、JavaScriptでindeterminatetrueに設定されているとき
  • <progress>要素で、途中のとき

:in-range

<input>要素で入力値がminmax属性による範囲内にあるものに一致します。

:out-of-range

<input>要素で入力値がminmax属性による範囲外にあるものに一致します。

:optional

required属性が設定されていない<input><select><textarea>要素と一致します。

:placeholder-shown

プレースホルダが表示されている<input><textarea>要素と一致します。

:read-only

読み取り専用readonlyが指定されている要素と一致します。

:read-write

ユーザが編集可能な要素と一致します。

:required

<input><select><textarea>要素でrequired属性が与えられているものと一致します。

:valid

バリデーションが成功したフォーム要素と一致します。

:invalid

バリデーションが失敗したフォーム要素と一致します。

リンク関連

:any-link

href属性を持つ全ての<a><area>と一致します。

:link

href属性を持つ<a><area>のうち、未訪問の要素と一致します。

:visited

href属性を持つ<a><area>のうち、訪問済みの要素と一致します。

プライバシー上の理由から、適用できるスタイルに制約があります。

  • 利用できるCSSプロパティは以下の通り
    • color
    • background-color
    • border-color(ショートハンドではないものも含む)
    • column-rule-color
    • text-decoration-color
    • text-emphasis-color
  • 利用できるSVG属性はfillstroke
  • 利用できるスタイルでもアルファチャンネルは無視される
  • <link>要素は:visitedに一致することはない
  • window.getComputedStyle2メソッドは:visited状態ではない色の値を返す

:target

URLの#で記述するフラグメントに一致するidを持つ要素と一致します。

テキスト関連

:lang()

指定された言語に一致する要素を選択します。
つまり、言語別にスタイルを適用することが出来ます。

画面の状態

:fullscreen

全画面モードの要素に一致します。複数あればすべて選択します。

:picture-in-picture

ピクチャインピクチャモードの要素に一致します。

印刷

すべて@pageアットルールで使用されます。

:first

印刷文書の最初のページと一致します。

文書のマージン、改ページするとき前ページに印刷する最低行数を設定するorphans、改ページするとき次ページに印刷する最低行数を設定するwindows、ページ区切りを変更することが出来ます。
また、マージンはpxinなどの絶対的な長さの単位のみ使用できます。

:left

印刷文書の左側のページと一致します。

ページのmarginpaddingborderbackgroundの各プロパティを変更することができます。

:right

印刷文書の右側のページと一致します。

疑似要素

疑似要素は、その要素の特定の部分に対してスタイルを付与することができるものです。
CSSで記述する際は、::beforeのように、コロンを2つつけます。

構文
selector::pseudo-element {
  property: value;
}

::after

選択した要素の子要素の最後に疑似要素を生成します。
<img><br>などの置換要素3には適用されません。

contentプロパティを用いて、要素の装飾によく使われます。
また、contentは空にして、backgroundに画像を設定したりして装飾することも多いです。

疑似クラスと疑似要素を見分けやすくするために、CSS3でコロン2つの表記法::afterが導入されましたが、CSS2の:afterも使用することが出来ます。

::before

選択した要素の子要素の最初に疑似要素を生成します。
その他::afterと同様です。

::backdrop

Experimentalではありますが、この要素自体はほぼ全てのブラウザで使用可能になったので記載します。
Experimentalが外されました。

何らかの要素が全画面モードで表示されたときにそのすぐ下のレイヤーに表示されるViewportサイズのボックス要素です。
これはFullscreen APIを使用して全画面モードで配置される要素やおよび<dialog>MDN Web Docs参照)要素を表示するときに用いられます。

全画面モードで複数の要素が配置されたときは、::backdropは最上位要素のすぐ下に描画されます。

::backdropはどの要素にも継承せず、どの要素からも継承せず、プロパティの制限もありません。

::cue

選択された要素内のWebVTTキューを指定します。VTTトラック付きのメディアで、キャプションなどをスタイル付けすることができます。WebVTTについてはこちらを参照してください。

使用可能なプロパティ

::first-letter

ブロックレベル要素の最初の行の一番最初の文字を指定します。ただし、最初の文字より前に他のコンテンツがない場合に限ります。

単純に要素の最初の文字を識別できるとは限らないため注意が必要です。
例えば、::beforecontentプロパティで、要素の先頭にテキストが挿入された場合、この挿入されたコンテンツの最初の文字に一致します。

利用可能なプロパティ

::first-line

ブロックレベル要素の最初の行を指定します。
なお、選択できる最初の行の長さは、要素・文書の幅、文字列のフォントの大きさなど、様々な要因に左右されます。

利用可能なプロパティ

::file-selector-button

type="file"input要素を指定します。
「ファイルを選択」のようなボタンにスタイルを適用することができます。

古いWebKit/Blink互換のブラウザは-webkit prefixが必要です。(::-webkit-file-upload-button

::selection

ユーザーがテキストをマウスでクリックやドラッグすることで選択した文書の一部にスタイルを適用します。

利用可能なプロパティ

  • color
  • background-color
  • text-decoration
  • text-shadow
  • SVG関連 (stroke-color, fill-color, stroke-width)

::slotted()

HTMLテンプレート内にあるスロットに配置された任意の要素を指定します。
テンプレートとスロットについて

これはshadow DOM内に配置されたCSSの中で使われた時のみ機能します。

/* スロット内に配置された任意の要素を選択 */
::slotted(*) {
  font-weight: bold;
}

/* スロット内に配置された<span>要素を選択 */
::slotted(span) {
  font-weight: bold;
}

まとめ

以上、疑似要素と疑似クラスについてまとめました。

知らなかった要素もちらほらあり、自分もぜひ活用していきたいと思います。

参考

  1. Shadow DOM: Light DOMから独立したツリー構造

  2. アクティブなスタイルシートに含まれるすべてのCSSプロパティの値を含むオブジェクトを返すメソッド

  3. 文書スタイルに影響されない要素。要素ボックス内のコンテンツ位置を設定できるプロパティのみが影響を与えることができる

11
15
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
11
15