Skip to content
This page has been auto-translated and may contain errors.View in English

CSSセレクター

docs.scrimba.com

ページが要素でいっぱいで、適用したいスタイルのセットがあります。しかし色やフォントは、どの要素に属するかを指定できるまでは役に立ちません。セレクターは正しい要素を指し示す方法です。この段落、すべてのボタン、navの中のリンクだけ。セレクターに慣れれば、CSSの残りはどの要素を変更するかを選ぶだけになります。なぜなら、既にそこにアクセスする方法を知っているからです。

要素型、クラス、ID セレクター

CSSルールには2つの部分があります。スタイルする要素を選ぶ**セレクター**と、どのようにするかを指定する宣言ブロックです。最も単純なセレクターは、要素型セレクターと呼ばれる要素の名前です。pと書くと、ページのすべての段落がスタイル設定されます。

これは多すぎることがよくあります。通常、すべての段落を同じように見せたくはありません。そこで、HTMLclass属性を使って要素にクラスというラベルを付け、CSSからドットを前に付けてそのラベルをターゲットにします。クラスは名札のようなものと考えてください。グループとして扱いたいすべての要素に同じタグをピンで留め、そのタグを一度スタイル設定します。

要素をターゲットする3つの基本的な方法があります。**要素型セレクター**はタグ名でマッチします(pはすべての段落にマッチします)。クラスセレクターはclass属性でマッチし、先頭にドットを付けて書きます(.button)。IDセレクターはid属性でマッチし、先頭にハッシュを付けて書きます(#header)。

スタイリングフックのデフォルトとしてクラスを使用します。クラスは好きなだけ多くの要素に付けることができ、1つの要素は複数のクラスを持つことができるため、クラスは再利用可能なグループを説明します。.cardを持つすべてのものは同じ外観を共有します。要素型セレクターは広範なベーススタイル設定に便利です(例えば、bodyのフォントを設定することなど)が、その種類のすべての要素に当たるため、都合が悪いです。IDはページ内で一意である必要があるため、それらを通じてスタイル設定することはルールを単一の要素にロックし、詳細度で見られるように、それらはオーバーライドを難しくする追加の重みを持ちます。

3つのセレクタータイプは基本をカバーし、それらの間の違いは部分的にマッチングについてで、部分的に重みについてです。要素型セレクター(タグまたは要素セレクターともいう)は要素名でマッチします。psectioninputなど。クラスセレクター(.cardと書く)はclass属性にそのトークンが含まれる要素にマッチしており、属性はスペースで区切られているため、1つの要素は多くのクラスを保持できます。IDセレクター(#headerと書く)はid属性がその値に等しい単一の要素にマッチします。IDはドキュメント内で一意である必要があります。

実際のルールは、ほぼ専門的にクラスを通じてスタイル設定することです。クラスは、再利用可能でありながら詳細度が低い唯一のセレクター型です(詳細度はブラウザーが競合を解決するのに使用する優先度スコアで、この章の最後でカバーされます)。これにより、スタイルは平坦で上書き可能のままです。要素型セレクターは小さなセットのベースルールに属しています。リセット、body上のデフォルトフォント、aまたはinput上の妥当なデフォルト。IDはJavaScriptフックおよびフラグメントリンクターゲット(URLの#pricing)として正当ですが、スタイリングフックとしてはトラップです。それらは一意であるため、グループを説明することはできず、その高い詳細度は、後のクラスルールがエスカレーションなしでそれらをオーバーライドできないことを意味します。クラスでスタイル設定し、IDをアンカーとスクリプト用に予約します。

html
<button class="btn-primary">申し込む</button>
<button class="btn-primary">今すぐ購入</button>
css
/* 要素型セレクター: ページ上のすべてのボタン */
button {
  font-family: inherit;
}

/* クラスセレクター: btn-primaryタグ付きの要素のみ */
.btn-primary {
  background: rebeccapurple;
  color: white;
}

両方のボタンは1つのルールから.btn-primaryスタイルを取得します。なぜなら、それらはクラスを共有しているためです。その再利用は、クラスに手を伸ばす理由全体です。これはCSSがどのように機能するかに直接構築されています。ここで各ルールはセレクターと宣言のセットをペアリングします。

Juno要素型、クラス、ID セレクターpのような要素型セレクターはその種類のすべての要素にヒットし、通常はあなたが望むより多くです。クラスはあなたが気になる要素にピンで留める名札で、btn-primaryのようにドットでスタイル設定します。ほぼすべてにクラスから始めれば、大きく間違えることはありません。
Juno要素型、クラス、ID セレクター クラスはあなたのデフォルトフック。再利用可能で、1つの要素は複数のクラスを持つことができます。広いベーススタイル(bodyのフォントなど)はクラスセレクターのために予約しておき、IDはスタイル設定には特異性が高すぎて単一用途のため扱います。自分自身を将来の頭痛から救い、最初にクラスに手を伸ばしてください。
Juno要素型、クラス、ID セレクター クラスは再利用可能でありながら詳細度が低い唯一の基本的なセレクターであり、それはまさにあなたがそれらを通じてスタイル設定し、ルールを平坦に保つ理由です。要素型セレクターはそれらの小さなベースレイヤーでその場所を獲得し、IDはスクリプトとリンクアンカーに属し、スタイル設定には属しません。IDルールが後のクラスによってオーバーライドされることを拒否する日には、あなたはそれらを除いておいてよかったと思うでしょう。

コンビネーター: 関係性によるセレクション

時には別の要素の中にある場合にのみ要素をスタイル設定したいことがあります。ナビゲーション内のリンクは、段落内のリンク(どちらも<a>要素)とは異なる外観を持つはずです。その関係を**コンビネーター**で説明します。2つのセレクターをスペースで並べてください。CSSはそれを「2番目のもの、ただし最初のもの内のみ」と解釈します。

つまり、.nav aは「クラスnavを持つ要素内の任意のリンク」を意味します。ここではスペースが実際に機能しています。装飾ではなく、内部を見る指示です。

**コンビネーター**は2つのセレクターを結合し、HTML内でそれらがどのように関連しているかに基づいてマッチします。最も一般的なのはディセンダント(子孫)コンビネーターで、スペースとして書かれます。.nav a.nav内のどこかにある<a>にマッチします。ネストがどれだけ深くても関係ありません。

直接の子だけが必要で、より深い子孫ではない場合は、チャイルドコンビネーター>を使用します。.menu > li.menuの直接の子であるリスト項目にマッチし、ネストされたリストをスキップします。親を共有する要素について2つのシブリングコンビネーターもあります。隣接シブリング+は別のもののすぐ後の要素にマッチし(h2 + pは見出しの直後の段落をスタイル設定します)、一般的なシブリング~は後続するシブリングにマッチします。ディセンダントとチャイルドが大部分の実際の作業をカバーします。シブリングコンビネーターは間隔とフォームパターンに便利です。

**コンビネーター**は2つのセレクター間の文字で、それらが満たす必要がある構造的な関係を定義します。ディセンダント(子孫)コンビネーター(スペース)は、右側のセレクターが左側の内部のどこかにネストされている場合にマッチします。任意の深さで。チャイルドコンビネーター(>)はそれを直接の子のみに制限します。.menu > liはネストされた.submenuに埋もれたリスト項目を無視します。隣接シブリングコンビネーター(+)は別のシブリングのすぐ後で親が同じ要素にマッチし、一般的なシブリングコンビネーター(~)は親が同じ後続するシブリングにマッチします。

本番環境で保持する価値があることが2つあります。まず、複合セレクターはブラウザーのマッチャーで右から左へ読まれます。.nav aについては、エンジンは最初に<a>要素を検出してから、各々が.nav祖先を持つかどうかをチェックするために上へ移動します。これが長いディセンダントチェーンがより多くのコストがかかり、なぜ厳しい.nav > aがゆるい.nav aより安い可能性があるかです。次に、ディセンダントセレクターはあなたのCSSをあなたのマークアップ構造に結合します。.card .titleは誰かがタイトルを別の要素でラップした瞬間に壊れます。要素に直接クラスを使用(.card-title)し、関係が実際に表現したいものである場合にのみコンビネーターにドロップすることで、スタイルをマークアップ変更に強くします。

css
/* ディセンダント: navの内部の任意のリンク */
.nav a {
  text-decoration: none;
}

/* チャイルド: .menuの直接の子であるリスト項目のみ */
.menu > li {
  display: inline-block;
}

最初のルールはnavの内部にネストされたすべてのリンクに到達します。2番目はメニューの最上位の項目のみに到達し、ネストされたリストは放置します。それらの間を選ぶことは、ルールがどこまで下へ移動するかを選ぶことです。

Junoコンビネーター 2つのセレクター間のスペースは「内部」を意味します。nav aはnavの内部に座るリンクをスタイル設定します。そのスペースは指示であり、見た目のための間隔ではありため、誤ってドロップしないでください。このパターンだけで多くの日常的なスタイル設定がカバーされます。
Junoコンビネーター スペースはディセンダント(子孫)コンビネーターで任意の深さでマッチします。>はそれを直接の子のみに絞ります。シブリング+~は前に何が来るかに基づいて要素をスタイル設定する必要があるときにそこにあります。ディセンダントとチャイルドは日々、ほぼすべてを処理します。
Junoコンビネーター コンビネーターは有用ですが、あなたのCSSをあなたのHTML構造に結合するため、.card .titleのような長いディセンダントチェーンはリファクタリングから1つ離れています。要素に直接クラスを使用して、関係が実際にあなたが表現したいことであるときにのみコンビネーターにドロップしてください。マッチングも右から左へ実行されるため、厳しい>はゆるいディセンダントチェーンを上回ることがよくあります。

疑似クラス: 状態によるスタイル設定

要素はさまざまな状態にある可能性があります。リンクは静止しているか、マウスがその上にホバーしているかもしれません。**疑似クラス**により、要素をその状態に基づいてスタイル設定でき、セレクターの後に単一のコロンで記述されます。

最初に使用するのは:hoverです。.btn-primary:hoverと書いて、ポインターがボタンの上にある間だけそれらのスタイルが適用されます。これはボタンとリンクがあなたがそれらを指すと小さな視覚的応答をする方法です。

**疑似クラス**は特定の状態または位置にある要素をターゲットにし、単一のコロンで書かれます。:hoverはポインターがその上にある間、:focusはキーボード入力用に選択されている場合、:first-childはそれが親内の最初の要素の場合。

:focusはアクセシビリティー上の懸念事項であるため、注目に値します。キーボードで移動する人々は1つのコントロールから次へタブして、:focusスタイルは彼らがどこにいるかを示す唯一の信号です。フォーカスアウトラインを削除しないでください。可視の代替案で置き換えずに。また、:nth-child()をとる:first-child:last-childなどの構造的疑似クラスがあり、括弧の中のパターンをとります。:nth-child(odd)はすべての他の要素にマッチし、テーブル行をストライプするのに便利です。:first-child:last-childは追加のクラスなしでグループの端を取ります。

疑似クラス(単一のコロンの後のキーワード)は、マークアップを追加することなく、与えられた状態または構造的な位置にある要素にマッチします。状態疑似クラスには:hover:active:focusが含まれます。構造的なものには:first-child:last-child、パラメーター化された:nth-child()があり、その引数はan+bパターンです(:nth-child(2n)はすべての2番目の要素、:nth-child(3n+1)は3つのグループの最初の要素です)。

2つの本番環境のメモ。:focusはキーボードアクセシビリティーにおいて非交渉的です。キーボードユーザーは自分の位置を知るためにフォーカスリングに依存しているため、可視の置き換えなしにアウトラインを削除すると、それらにとってインターフェースは使用不可能になります。:focus-visibleを選択してください。これはキーボード対話でリングを表示しますが、マウスクリックではそれを抑制するため、クリーンなポインター体験とアクセシブルなキーボード体験の両方を得ます。構造的な側面では、:nth-child(n)はタイプに関係なくすべてのシブリングをカウントします。一方、:nth-of-type(n)は同じ要素のシブリングのみをカウントしており、これはルールが機能することと、迷走した要素がリストに座っている場合にサイレントに誤数えするものとの違いです。

css
.btn-primary:hover {
  background: purple;
}

/* キーボードユーザーは可視フォーカスインジケーターが必要 */
.btn-primary:focus-visible {
  outline: 2px solid rebeccapurple;
  outline-offset: 2px;
}

最初のルールはポインターがボタンの上にある間に発火します。2番目は、ボタンがキーボードで選択されたときにクリアなリングを描画し、これはページをマウスなしで使用可能に保つものです。ここでの色とアウトラインの選択はCSSがどのように機能するかとあなたが設定する値に接続します。任意のプロパティ。

Juno疑似クラス 疑似クラスは要素を特定の状態でスタイル設定し、:hoverのような1つのコロンで書かれます。ポインターがそれの上にあるときのためにそれです。それはセレクターに直接付け、その間にスペースはありません。
Juno疑似クラス 疑似クラスはマッチ状態と位置: :hover:focus:nth-child():first-child:focusをアクセシビリティー要件として扱ってください。キーボードユーザーは自分がどこにいるかを見る必要があるため、可視の置き換えなしでアウトラインを削除しないでください。その習慣はすべての人にとってページを使用可能に保ちます。
Juno疑似クラス :focusよりも:focus-visibleに手を伸ばし、リングはキーボードユーザーに対しては表示されますが、マウスクリックではそれを抑制し、フォーカスインジケーターを完全に削除するインターフェースを配信しないでください。:nth-child:nth-of-type`トラップを見てください。1つはすべてのシブリングをカウントし、他方は同じタイプシブリングのみをカウントし、誤った選択は迷走した要素がリストに着地した瞬間に誤数えします。それは細かいように見える種類のバグですが、何もしません。

疑似要素: 要素の一部をスタイル設定する

疑似クラスはある状態全体の要素をスタイル設定します。**疑似要素**は異なります。要素の一部をスタイル設定するか、HTMLに全くない小さなコンテンツを追加することができます。

最初に会う2つは::before::afterです。それらは要素の開始時点の終了時点にコンテンツを挿入し、あなたはcontentプロパティを使用して何を挿入するかを伝えます。2つのコロンに注意してください。その二重コロンはCSSが疑似要素を疑似クラスから区別する方法です。

**疑似要素**は全体ではなく要素の特定の部分をスタイル設定し、二重コロン(::)を使用して単一コロンの疑似クラスと区別します。最も使用されるのは::before::afterで、要素の最初または最後に生成された子を作成します。それらがレンダリングするためにcontentプロパティを必要とします。空(content: "")であっても、その生成されたコンテンツはデコレーティブです。スクリーンリーダーはそれをスキップする可能性があるため、意味をそこに置かないでください。

もう1つ一般的なのは::placeholderで、これは空の入力の中にかすかなヒントテキストをスタイル設定します。疑似要素は要素のスライスをターゲットにするため、追加のタグをマークアップに追加することなく、小さなビジュアルピース(ラベルの前のアイコン、見出しの後の装飾線)を構築できます。

**疑似要素**は独自のタグを持たない要素の一部を公開し、二重コロンキーワードを使用してスタイル設定されます。::before::afterは、要素の最初または最後の子としてインラインボックスを生成します。contentが設定されたときのみレンダリングします(純粋にデコレーティブなボックスについてはcontent: ""を使用)、その生成されたコンテンツはアクセシビリティー木の外に座り、装飾的である必要があり、ユーザーが必要とする意味を持つことはありません。::placeholderは入力のヒントテキストをターゲットにし、::selectionはハイライトされたテキストをターゲットにし、::first-line::first-letterは組版スライスをターゲットにします。

単一対二重コロンの話は知る価値があります。モダン疑似要素は::(2つのコロン)を使用して疑似クラスから分離し、CSS3で導入された区別です。4つの元の疑似要素(:before:after:first-line:first-letter)については、レガシー理由から単一コロン形式も解析されていますが、二重コロン形式を書いてください。単一コロンはレガシー互換性の遺物であり、新しいコードに持ち込むべきスタイルではありません。本番環境では、::before::afterは多くの静かな作業をしています。ツールチップ、カスタムリストマーカー、古いレイアウトのclearfix、HTMLを乱雑にする別の装飾の花びら。

css
/* すべてのnavリンクの後に装飾矢印を追加 */
.nav a::after {
  content: " →";
  color: rebeccapurple;
}

/* 検索ボックス内のヒントテキストをスタイル設定 */
.search-input::placeholder {
  color: grey;
  font-style: italic;
}

::afterルールは矢印を挿入し、HTMLではなく、スタイリング内にのみ存在します。一方、::placeholderは入力内に到達して、ブラウザーが描画するテキストをスタイル設定します。どちらも平文セレクターで到達できないものをスタイル設定します。ヒントテキストとラベルをスタイル設定している場合、タイポグラフィー章はテキスト側についてさらに深く掘り下げています。

Juno疑似要素 疑似要素は要素の一部をスタイル設定するか、少しのコンテンツを追加し、::before::afterのような2つのコロンを使用します。これら2つは表示されるためにcontentプロパティが必要です。二重コロンは疑似要素を疑似クラスから分ける速い方法です。
Juno疑似要素 疑似要素は二重コロンを使用し、要素のスライスをスタイル設定します。::before::after::placeholder。最初の2つはcontent値を必要とし、空の""でさえも、そのコンテンツはデコレーティブであり、実際の意味をHTMLに保ちます。それらはタグのみを追加することから保存されます。
Juno疑似要素 疑似要素を2つのコロンで書いてください。単一コロン形式は4つの元のレガシークォークのためだけに生きています。::before::afterからのコンテンツはアクセシビリティー木の外に住んでいるため、それは装飾的であり、ユーザーが読む必要があるものを持つことはありません。それらは静かにツールチップ、カスタムマーカー、マークアップを膨らませるだけの装飾を処理します。

詳細度: どのルールが勝つか

早かれ遅かれ2つのルールが異なる方法で同じ要素をスタイル設定しようとします。1つはテキストが青であると言い、別のものはそれが赤であると言います。ブラウザーは1つを選択する必要があり、決定する方法を**詳細度**と呼びます。より具体的なセレクターが勝ちます。

短いバージョンは強さの順です。IDセレクターはクラスセレクターを上回り、クラスセレクターは要素型セレクターを上回ります。だから、#header.titleの両方が同じ要素に色を設定する場合、IDが勝ちます。2つのルールが同じ詳細度の場合、ファイルの後半で記述されたものが勝ちます。

複数のルールが同じ要素をターゲットにして同じプロパティを設定する場合、ブラウザーは**詳細度**で競合を解決します。これは関連するセレクターの種類に基づいたスコアです。最強から最も弱いへの順序は、インラインスタイル(要素のstyle属性)、IDの順です。次に、クラス(および疑似クラスおよび属性セレクター)、その後の要素型セレクター(および疑似要素)。より具体的なセレクターがソース順序に関係なく勝ちます。詳細度が関連付けられた場合、後のルールが勝ちます。

これはクラスに依存し、スタイル設定のためのIDを避けるための実践的な理由です。IDでスタイル設定する場合、後のクラスルールはそれらをオーバーライドできないため、エスカレーションで終わります。また、宣言に追加できる!importantは、宣言がすべてをオーバーライドするために強制し、最後の手段として扱われるべきです。これは通常のカスケードを壊し、1つの!importantを破ることの唯一の方法は別の方法であり、それは始めたくないスパイラルです。

**詳細度**は、競合する宣言の間でブラウザーが選ぶために使用するアルゴリズムです。これは、多くの場合(a, b, c)と書かれた3部構成のカウントとして計算されます。aはIDセレクターの数、bはクラス、属性、疑似クラスセレクターの数、cは要素型と疑似要素セレクターの数です。パーツは左から右へ比較し、任意のIDはクラスの任意の数を上回り、任意のクラスはタイプセレクターの任意の数を上回ります。#header .title a(1, 1, 1)をスコアし、.nav .menu .item a(0, 3, 1)をスコアします。最初は単独でIDで勝ちます。インラインstyle属性はすべてのセレクター詳細度の上に座り、!important(値に追加するフラグを強制するフラグ)はそれでも上書きします。ユニバーサルセレクター*とコンビネーターはスコアに何も追加しません。

2つのモダンツールはこれを管理する方法を変更します。:is()はセレクターのリストを取り、それらのいずれかがマッチする場合にマッチしますが、最も具体的な引数の詳細度を取るため、:is(#header, .title)はIDの重みを継承します。:where()は同じマッチングをしますが、常に0の詳細度を持っています。これはあらゆるものがオーバーライドできる低重量ベーススタイルを書くためのツールです。:has()は関係的疑似クラスであり、要素が何かを含むものにマッチします(「画像を持つ.card」、.card:has(img))そして引数の詳細度を取ります。これすべての下にある保守性の実践は、詳細度を低く平坦に保つことです。単一クラスセレクターを選択し、IDと!importantを避け、デフォルトが生成したいスタイル設定でゼロアウト体重をするために:where()を使用します。平坦な詳細度は、後のルールが後で勝つことができることを意味し、これはカスケードがあなたに対して働く代わりにあなたのために働いています。

css
/* 要素型セレクター、詳細度 (0, 0, 1) */
p {
  color: grey;
}

/* クラスセレクター、詳細度 (0, 1, 0): このものが勝つ */
.intro {
  color: black;
}
html
<p class="intro">この段落はクラスルールが要素型ルールを上回るため、黒です。</p>

両方のルールは段落をターゲットにして両方がcolorを設定しますが、クラスセレクターは要素型セレクターより具体的なため、段落は黒です。1つのセレクターを詳細度ラダーの上または下に調整することは、より重いツールに頼ることなく競合を解決するためにしばしば必要なすべてです。ボックスモデル章は間隔ルールが衝突するときに同じカスケードに実行されます。

Juno詳細度 2つのルールが同じ要素をめぐって戦う場合、より具体的なものが勝ちます。IDはクラスを上回り、クラスは要素型セレクターを上回ります。それらが同じ詳細度の場合、ファイルの最後にあるものは何でも勝ちます。それはほぼすべての競合を説明しています。
Juno詳細度 強さはインラインで実行され、その後ID、その後クラス、その後タイプであり、より具体的なルールがファイルのどこに座ろうが勝ちます。これはなぜクラスでスタイル設定し、IDを避けることがあなたのCSSを上書き可能に保つかです。!importantを最後の手段として保ちます。それを上回るもう1つのものだけです。
Juno詳細度 詳細度は(a, b, c)としてID、クラス、タイプのカウント、左から右へ比較します。1つのIDはクラスの任意の山を上回ります。低く平坦に保ってください。単一クラス、スタイル設定用のIDなし、!importantなし、デフォルトが生成したいときに重みをゼロアウトするための:where()。平坦な詳細度は、後のルールが後で勝つことができることを意味し、そのカスケードはあなたと一緒に働いています。