CSS Kontextselektor: Nachbar-Selektoren

Nachbar-Elemente

Ein Nachbar- oder Adjacent-Selektor (Pluszeichen) findet ein Elemente direkt nach einem Element – ein Nachbar- oder Geschwister-Element – oder alle Elemente vor und nach einem Element (mit dem Tilde-Symbol ~), die auf derselben Ebene liegen, also dasselbe Elternelement haben.

Direkter Nachbar – Adjacent: Element + Element

Das Pluszeichen zwischen zwei Selektoren fordert die direkte Nachbarschaft: Das zweite Element muss direkt auf das erste Element folgen. Genauso wie Nachkommen- und Kind-Selektoren kombinieren sie CSS-Selektoren und stellen Beziehungen zwischen zwischen ihnen her.

Beispiel: ein p direkt hinter h2
CSS adjacent Elements: Beispiel: ein p direkt hinter h2
h2 + p {
	color: white;
	background-color: red;
}

Nachbar-Selektor, angewendet auf ein p-Element, das dem h2-Element direkt folgt. h2 und p sind direkte Nachbarn und haben dabei immer dasselbe Eltern-Element.

Indirekte Nachbarn: Element ~ Element

Der indirekte Nachbar-Selektor (beim W3C als Subsequent-sibling combinator bezeichnet) wird durch ein Tilde ~ angelegt (HTML-Entity ∼ wie similar, ähnlich).

Ein Subsequent Sibling Selektor spricht alle p-Elemente an, die dem h2-Element folgen. h2 und p haben dabei immer dieselben Eltern – liegen in derselben Ebene.

Beispel: child-selector alle p direkt unter div
CSS Subsequent Siblings
h2 ~ p { color: white; background-color: red; }

Anders als beim direkten Nachbar-Selektor müssen die Nachbarn nicht direkt aufeinander folgen. Im Beispiel oben liegt ein ul-Element zwischen den p-Elementen.

Beispiel für die Anwendung von indirekten Nachbar-Selektoren: CSS Akkordeon ohne Javascript.

Beispiel: Nachbar-Selector als CSS-Zähler

Der indirekte Nachbar-Selector funktioniert als CSS-Rechner: Wieviele Elemente hat ein Block – ohne Javascript-Einsatz? Dann müssen wir z.B. bei einem Flex-Element nicht wissen, wieviele Element vorkommen, sondern können es dem CSS der Elemente die Gestaltung überlassen.

Um herauszufinden, ob ein Element das einzige Kind seines Elternelements ist, reicht schon der only-of-type-Selektor.

.card:only-of-type { 
	background-color: thistle;
	width:100%;
}

.card:nth-last-child(2):first-child, 
.card:nth-last-child(2):first-child ~ .card {
	background: cornflowerblue;
	width: 46%;
}

.card:nth-last-child(3):first-child, 
.card:nth-last-child(3):first-child ~ .card {
	background: lightslategray;
	width: 30%;
}

.card:nth-last-child(4):first-child,
.card:nth-last-child(4):first-child ~ .card {
	background: honeydew;
	width: 46%;
}
  • Der nth-last-child-Selektor findet das letzte Element an Stelle n (damit haben wir die Anzahl).
  • .card:nth-last-child(2):first-child trifft auf das erste Element der Nachbarschaft.
  • Jetzt kommt der indirekte-Nachbar-Selektor ins Spiel: der sucht alle indirekten Nachbarn – also alle Elemente der Ebene.

Der Abzählreim hört nicht bei vier Elementen auf, selbst 101 Elemente singen im Chor.

Kombination mit class

Auch diese Kontext-Selektoren können z.B. durch Klassen- oder id-Selektoren noch weiter eingeschränkt werden.

div#nurHier p.content { color: white; background-color: green; width: 500px; }

Nur Inhalte von p-Elementen mit dem Attribut class="content", die innerhalb des div-Elements mit dem id-Attribut id="nurHier" liegen, werden den aufgeführten Regeln unterworfen.

Kontext-Selektoren und Performance

Diese Selektoren sind zwar sehr mächtig und zudem im Stylesheet gut lesbar, sie kosten aber auch Performance vom Browser.

Wir lesen einen Kontext-Selektor wie hier von links nach rechts

#content article .main p span { color: blue; }

…

<div id="content">
   <article>
      <div class="main">
         <p>Wahrscheinlich waren es <span>Stunden</span> über 
            Stunden, die …</p>
      </div>
   </article>
</div>

Wenn in #content ein article-Tag steht und darunter ein Element mit der Klasse .main in dem ein p liegt und darin ein span – dann rendere den Inhalt Blau.

Der Browser löst die Eigenschaft aber von rechts nach links auf: Der Browser sucht erst alle span-Elemente, dann filtert er die span-Elemente, die in p-Tags liegen … usw.

So elegant Kontext-Selektoren auch sind – für schnelle Reaktionszeiten sollten sie sparsam und bewußt verwendet werden.