From 48333ff207d988231a0d13c1d633adf8a2914a2a Mon Sep 17 00:00:00 2001 From: Denis Ergin Date: Mon, 25 Nov 2024 17:06:01 +0100 Subject: [PATCH] feat(slides): add slides for advanced css selectors --- .../css-selectors-advanced/advanced.astro | 128 +++++ .../slides/css-selectors-advanced/index.astro | 228 +++++++++ .../css-selectors-advanced/introduction.astro | 8 + .../media-queries.astro | 196 +++++++ .../css-selectors-advanced/nth-box.astro | 33 ++ .../css-selectors-advanced/pseudo.astro | 482 ++++++++++++++++++ .../slides/css-selectors-advanced/title.astro | 3 + src/pages/slides/css-selectors-advanced.astro | 8 + 8 files changed, 1086 insertions(+) create mode 100644 src/components/slides/css-selectors-advanced/advanced.astro create mode 100644 src/components/slides/css-selectors-advanced/index.astro create mode 100644 src/components/slides/css-selectors-advanced/introduction.astro create mode 100644 src/components/slides/css-selectors-advanced/media-queries.astro create mode 100644 src/components/slides/css-selectors-advanced/nth-box.astro create mode 100644 src/components/slides/css-selectors-advanced/pseudo.astro create mode 100644 src/components/slides/css-selectors-advanced/title.astro create mode 100644 src/pages/slides/css-selectors-advanced.astro diff --git a/src/components/slides/css-selectors-advanced/advanced.astro b/src/components/slides/css-selectors-advanced/advanced.astro new file mode 100644 index 0000000..c37f9a1 --- /dev/null +++ b/src/components/slides/css-selectors-advanced/advanced.astro @@ -0,0 +1,128 @@ +
+
+

Erweiterte Selektoren

+
+ +
+

Soweit haben wir "einfache" Selektoren gesehen, die verwendet werden um Elemente anhand des Element-Types (z.B. span, p, div), oder dessen Attribute auszuwählen.

+

Dies ist aber nicht immer ausreichend, um alle Fälle in der Alltagsarbeit abzudecken.

+
+ +
+

Child Selektierung

+
+ +
+

In der HTML Dokumentenstruktur kann es häufig vorkommen, dass Elemente innereinander verschachtelt sind und Kindes-Elemente öfters den gleichen Klassennamen erhalten.

+

Mit einer einfachen Selektierung der Klasse kann es deshalb dazu kommen, das Elemente gestyled werden, die man eigentlich "nicht anfassen will".

+

Hierfür gibt es die Möglichkeit, Eltern-Elemente mit einer bestimmten Klassen zu definieren und Kinder mit bestimmten Klassen darin modifizieren/selektieren.

+
+ +
+

+      // Style das Element mit der Klasse "inner"
+      // das sich innerhalb eines Elementes mit
+      // der Klasse "zwei befindet"
+      .eins .inner {
+        background-color: #bfc; // Hellgrün
+      }
+
+      .zwei .inner {
+        background-color: #9ff; // Hellrot
+      }
+    
+
+ +
+
+
.eins .inner (erscheint Hellgrün)
+
+ +
+
.zwei .inner (erscheint Hellrot)
+
+ +
+ .inner (hat keine Hintergrundfarbe) +
+
+ +
+

Die Reihenfolge ist hierbei wichtig, eine beliebige Tiefe mit mehreren Kindes-Kindern ist auch möglich.

+

Es macht keinen Unterschied, ob das Kind-Element direktes Kind, oder verschachteltes Kind ist:

+
+ +
+
+
+
+
+ .eins .level-1 .level-2 .inner (erscheint Hellgrün) +
+
+
+
+
+ +
+

Wenn eine strengere Bindung notwendig ist, kann man dies mithilfe des "Child Combinator" Selektors tun.

+
+ +
+

Child Combinator

+
+ +
+

Der Child-Kombinator restriktiert die Selektion in dem Maß, dass ein Element ein direktes Child-Element zu einem Parent sein muss

+

Reduziert nochmals die Problematik, dass es zu ungewollten Selektionen von Elementen kommt

+
+ +
+

+      .parent > .child {
+        background-color: #f99;
+      }
+    
+
+ +
+
+
+ .parent > .child (roter Hintergrund) +
+
+ +
+
+
+ .parent > div > .child +
+
+
+
+ +
+

Sibling-Selektor

+
+ +
+

Mithilfe des Sibling-Selektors, lassen sich Elemente, die direkt nach einem anderen Element im Dokument erscheinen, selektieren.

+
+ +
+

+      .first + .second {
+        background-color: #f99;
+      }
+    
+
+ +
+
+ div.first +
+
+ div.second +
+
+
\ No newline at end of file diff --git a/src/components/slides/css-selectors-advanced/index.astro b/src/components/slides/css-selectors-advanced/index.astro new file mode 100644 index 0000000..e4d3c00 --- /dev/null +++ b/src/components/slides/css-selectors-advanced/index.astro @@ -0,0 +1,228 @@ +--- +import Title from "./title.astro"; +import Introduction from './introduction.astro'; +import Pseudo from './pseudo.astro'; +import Advanced from "./advanced.astro"; +import MediaQueries from './media-queries.astro'; +--- + +
+ + <Introduction /> + <Advanced /> + <Pseudo /> + <MediaQueries /> +</div> + +<style is:global lang="scss"> + .reveal pre code { + max-height: unset; + } + .apply-styles { + &.pseudo { + .container.first :first-child { + border: 4px solid #E58F65; + } + .container.first :first-letter { + color: red; + } + .container.second:first-line { + color: deeppink; + } + + .container.third p:first-of-type { + font-weight: bold; + color: royalblue; + } + + .container.fourth .child:nth-child(2) { + background-color: #E58F65; + } + .container.fourth :nth-child(4 of .child) { + background-color: #E58F65; + } + + .container.fifth { + :nth-child(even of .child) { + background-color: #E58F65; + } + :nth-child(odd of .child) { + background-color: rgb(126, 154, 240); + } + } + + .container.sixth { + .before-and-after { + &::before { + content: '>>before<<'; + background-color: rgb(255, 255, 172); + } + + &::after { + content: '>>after<<'; + background-color: rgb(255, 194, 201); + } + } + } + + .container.seventh { + .arrow-box { + padding: 1rem; + position: relative; + background: #88b7d5; + border: 4px solid #c2e1f5; + } + .arrow-box:after, .arrow-box:before { + top: 100%; + left: 50%; + border: solid transparent; + content: ""; + height: 0; + width: 0; + position: absolute; + pointer-events: none; + } + + .arrow-box:after { + border-color: rgba(136, 183, 213, 0); + border-top-color: #88b7d5; + border-width: 30px; + margin-left: -30px; + } + .arrow-box:before { + border-color: rgba(194, 225, 245, 0); + border-top-color: #c2e1f5; + border-width: 36px; + margin-left: -36px; + } + } + + .container.eighth { + button { + padding: 1rem 2rem; + border: none; + outline: none; + background-color: white; + border: 4px solid black; + border-radius: 1rem; + font-size: xx-large; + cursor: pointer; + box-shadow: 24px 24px 0 black; + transition: + box-shadow 50ms ease-in-out, + transform 50ms ease-in-out; + + } + + button:active { + box-shadow: 12px 12px 0 black; + transform: translateY(4px); + } + } + + .container.ninth { + display: flex; + justify-content: center; + + .card { + border: 4px solid black; + max-width: 300px; + padding: 2rem; + border-radius: 2rem; + box-shadow: 6px 6px 10px #0006; + transition: box-shadow 150ms ease-in-out; + } + + .card:hover { + box-shadow: 24px 24px 16px #0006; + } + } + } + + &.not { + p:not(.important) { + background-color: #282; + color: white; + } + + p.important { + background-color: #822; + color: white; + } + } + + &.not-where { + ul,ol {color: darkblue;} + ul,ol ul { color: darkred; } + ul,ol ol { color: darkred; } + ul,ol ul ol { color: darkgreen; } + } + + &.where { + :where(ol, ul) { color: darkblue; } + :where(ol, ul) :where(ol, ul) { color: darkred; } + :where(ol, ul) :where(ol, ul) :where(ol, ul) { color: darkgreen; } + } + + &.where-specifity { + p:where(.test) { + background-color: white; + } + + p { + background-color: #002; + color: white; + } + } + + &.is-specifity { + p:is(.test) { + background-color: white; + color: black; + } + + p { + background-color: #002; + color: white; + } + } + + &.child-selector { + font-family: monospace; + font-weight: bold; + + .eins .inner { + background-color: #bfc; + } + + .zwei .inner { + background-color: #f99; + } + } + + &.child-combinator { + font-family: monospace; + font-weight: bold; + + .parent > .child { + background-color: #f99; + } + } + + &.sibling { + font-family: monospace; + + .first + .second { + background-color: #f99; + } + } + + &.mq-first { + @media (width <= 900px) { + div.small-styled { + background-color: #f99; + } + } + } + } +</style> \ No newline at end of file diff --git a/src/components/slides/css-selectors-advanced/introduction.astro b/src/components/slides/css-selectors-advanced/introduction.astro new file mode 100644 index 0000000..5acdd04 --- /dev/null +++ b/src/components/slides/css-selectors-advanced/introduction.astro @@ -0,0 +1,8 @@ +<section> + <p> + Die bisher vorgestellten CSS-Selektoren, waren nur ein paar der Verfügbaren Methoden, um HTML-Elemente zu selektieren. + </p> + <p> + Die folgenden Slides erläutern die weiteren Methoden um komplexere Fälle abzudecken. + </p> +</section> \ No newline at end of file diff --git a/src/components/slides/css-selectors-advanced/media-queries.astro b/src/components/slides/css-selectors-advanced/media-queries.astro new file mode 100644 index 0000000..c2544c9 --- /dev/null +++ b/src/components/slides/css-selectors-advanced/media-queries.astro @@ -0,0 +1,196 @@ +<section> + <section> + <h2>Media Queries</h2> + </section> + + <section> + <p>Media Queries bilden einen Elementaren Bestandteil moderner Webentwicklung</p> + <p>Sie sorgen dafür, dass Elemente auf einer Website für mehrere "Viewports" angepasst werden.</p> + <p>Dadurch werden die Webseiten von heute "mobile Friendly". Sie sehen auf jedem Bildschirm gut aus (zumindest so die Theorie)</p> + </section> + + <section> + <p>Aber was machen Media Queries nun?</p> + <p>Am ehesten kann man Media Queries wie eine if-Abfrage für bestimmte Medien-Typen und Features funktionieren.</p> + <p><code>Wenn Bildschirm nicht breiter ist als 500px, dann "erwäge" folgende Selektoren und Styles...</code></p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + // Wenn Verfügbare Breite kleiner gleich 900 pixel ist... + @media (width <= 900px) { + // style div's mit Klasse "small-styled"... + div.small-styled { + background-color: #f99; + } + } + </code></pre> + </section> + + <section class="apply-styles mq-first"> + <div class="small-styled"> + Unter 900px habe ich einen roten Hintergrund! + </div> + </section> + + <section> + <p>Das ganze geht auch für eine Reihe von weitere Features:</p> + <ul> + <li>hover</li> + <li>prefers-color-scheme</li> + <li>width & height</li> + <li>orientation</li> + <li>Type</li> + </ul> + </section> + + <section> + <h3>Hover</h3> + </section> + + <section> + <p>Dient zur Feststellung, ob das Gerät ein einfaches hovern zulässt.</p> + <p>Dies ist Normal der Fall, wenn das Gerät einen Mauszeiger besitzt.</p> + <p>Geräte mit Toucheingabe fallen nicht in diese Kategorie.</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + @media (hover: hover) { + // Geräte, die ein "präzises" hovern zulassen, + // werden von Selektoren erfasst. + } + @media (hover: none) { ... } + </code></pre> + </section> + + <section> + <p>Touch-Geräte haben auch ein Gewisses "Hover"-Feature. Das hovern wird dabei ausgelöst wenn das Element angetippt wird und gleichzeitig der Finger vom Element wegbewegt wird.</p> + </section> + + <section> + <h3>prefers-color-scheme</h3> + </section> + + <section> + <p>Dieses Feature dient als Kommunikations-Schnittstelle zum Betriebssystem.</p> + <p>Im Betriebssystem kann heutzutage eingestellt werden, ob ein Light-Theme oder Dark-Theme in den Betriebssystem-Fenstern verwendet werden soll.</p> + <p>Mit <code>prefers-color-scheme</code> kann das abgefragt werden und Styles angewandt werden.</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + @media (prefers-color-scheme: light) { + // Betriebssystem-Standard-Einstellung + // Definiere Farben für helle Oberflächen (Light-Theme) + } + + @media (prefers-color-scheme: dark) { + // Definiere Farben für dunkle Oberflächen (Dark-Theme) + } + </code></pre> + </section> + + <section> + <h3>width & height</h3> + </section> + + <section> + <p>Wie vorhin bereits vorgestellt. Es lassen sich Unter- und Obergrenzen für breite und/oder Höhe definieren.</p> + <p>Es können auch mehrere Abfragen für verschiedene Display-Breiten (auch Viewports genannt) definieren</p> + <p>Mobile, Tablet, Small-Desktop, Large-Desktop sind "gängige" Benamungen</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + @media (width < 600px) { + // 599px und kleiner (mobile) + } + @media (600px =< width < 950px) { + // 600px bis 949px (tablet) + } + @media (950px =< width) { + // 950px und breiter (Desktop) + } + </code></pre> + </section> + + <section> + <h4>Mobile First!?</h4> + </section> + + <section> + <p>Eine gängige Taktik um Website-Inhalte zu implementieren, ist es "mobile-first" vorzugehen.</p> + <p>Dabei wird in der Implementierung zuerst die kleinste Viewport-Größe beachtet, sodass die Website auch auf kleinsten Geräten funktioniert.</p> + <p>Aktuelle Weiterentwicklung im Bereich der Webentwicklung deutet auf "Smallest Size First" hin.</p> + </section> + + <section> + <p>Bei Smalles-Size-First, wird mit neueren Queries (Container-Queries) die Verfügbare Breite eines Elementes (anstatt der gesamte Viewport) abgefragt.</p> + <p>Je nachdem wie viel Breite zur Verfügung steht können so Inhalte innerhalb eines Elementes unterschiedlich gestyled werden.</p> + </section> + + <section> + <h3>orientation</h3> + </section> + + <section> + <p>Besonders für Mobile Geräte interessant (wenn auch ein Computer-Bildschrim in Portrait dargestellt werden kann).</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + @media (orientation: portrait) { + // Hochkant (z.B. Normal gehaltenes Smartphone) + } + + @media (orientation: landscape) { + // Querformat (z.B. Computer-Bildschirm; Breiter als Höher) + } + </code></pre> + </section> + + <section> + <h3>Screen-Type</h3> + </section> + + <section> + <p>Die Definition des Screen-Types ist nur noch wichtig, wenn man seine Website als PDF generieren lassen will (bzw. Ausdruckbar machen will)</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + @media screen { + // Standard-Mäßige Darstellung von Inhalten + // Auf einem PC-Bildschirm + } + @media print { + // Spezielle Stylings für Druck-Inhalte (CMD+P oder CTRL+P) + } + </code></pre> + </section> + + <section> + Für ein Praxis-Beispiel, dient diese Webseite. Die Slides können auch als PDF exportiert werden. + </section> + + <section> + <h3>Verknüpfungen mehrerer Media-Queries</h3> + </section> + + <section> + <p>Manchmal ist es auch notwendig, mehrere Queries miteinander zu verknüpfen, man kann so komplexere Szenarien abbilden.</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + @media screen and (width <= 500px) { + // Kleine Bildschirme + } + + @media (500px <= width), screen and (orientation: portrait) { + // Kleine Breiten ODER Bildschirme im Hochkant-Modus + } + </code></pre> + </section> +</section> \ No newline at end of file diff --git a/src/components/slides/css-selectors-advanced/nth-box.astro b/src/components/slides/css-selectors-advanced/nth-box.astro new file mode 100644 index 0000000..8fd846a --- /dev/null +++ b/src/components/slides/css-selectors-advanced/nth-box.astro @@ -0,0 +1,33 @@ +--- +interface Props { + amount: number +} + +const { amount } = Astro.props; +--- + +<div class="flex"> +{ new Array(amount).fill(0).map((_, index) => ( + <div class="child"> + { index + 1 } + </div> +)) } +</div> + +<style> + .flex { + display: flex; + justify-content: center; + gap: 1rem; + } + + .child { + background: lightgray; + min-height: 150px; + min-width: 150px; + display: flex; + justify-content: center; + align-items: center; + } +</style> + diff --git a/src/components/slides/css-selectors-advanced/pseudo.astro b/src/components/slides/css-selectors-advanced/pseudo.astro new file mode 100644 index 0000000..984cba4 --- /dev/null +++ b/src/components/slides/css-selectors-advanced/pseudo.astro @@ -0,0 +1,482 @@ +--- +import NthBox from "./nth-box.astro" +--- + +<section> + <section> + <h2>Pseudo-Klassen</h2> + </section> + + <section> + <p>Pseudo-Klassen werden dazu verwendet, HTML-Elemente mit einem Bestimmten Zustand zu selektieren.</p> + <p>Ein paar Beispiele dieser Zustände sind: Erstes Element eines bestimmten Typs, Maus-Hover, und weitere.</p> + <p>Pseudo-Selektoren zeichnen sich dadurch aus, dass sie mit einem Doppelpunkt (":hover") gekennzeichnet sind.</p> + </section> + + <section> + <p><strong>first-child & first-letter</strong></p> + <p><code>first-child</code> selektiert das erste Vorkommende Kind innerhalb eines Element dar.</p> + <p><code>first-letter</code> selektiert den ersten Buchstaben innerhalb der Kinder eines Containers.</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + // Selektiere das erste Kind-Element innerhalb von .container + .container :first-child { + border: 4px solid #E58F65; + } + .container :first-letter { + color: red; + } + </code></pre> + </section> + + <section class="apply-styles pseudo"> + <p>Die Besten Programmiersprachen (nicht sortiert?):</p> + <ul class="container first"> + <li> + Javascript + <ul> + <li>TypeScript</li> + </ul> + </li> + <li>Rust</li> + <li>Python</li> + </ul> + </section> + + <section> + <p><code>:first-line</code></p> + <p>Mithilfe von Firstline, kann die erste Zeile (zum Beispiel in einem Paragraphen) gesondert gestyled werden</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + // Selektiere die erste Zeile im "container" + .container:first-line { + color: deeppink; + } + </code></pre> + </section> + + <section class="apply-styles pseudo"> + <p class="container second"> + Lorem ipsum dolor sit amet, consectetur adipisicing elit. Tempora sint, iure magnam, praesentium accusamus, fugit animi laboriosam aut ullam commodi nihil alias! Id provident numquam minus tempora ducimus ad natus. + </p> + </section> + + <section> + <p> + <code>:first-of-type</code> + </p> + <p>Mit diesem Pseudoselektor lässt sich ein bestimmtes Element innerhalb eines Containers selektieren</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + .container.third p:first-of-type { + font-weight: bold; + color: royalblue; + } + </code></pre> + </section> + + + <section class="apply-styles pseudo"> + <div class="container third"> + <p>Erster Paragraph</p> + <p>Zweiter Paragraph</p> + </div> + </section> + + <section> + <p>Nicht nur das erste Element selektieren: <code>nth</code>-Selektoren</p> + <p><code>first-child und first-of-type</code> lassen sich auch für Elemente an anderer als erster Stelle definieren:</p> + </section> + + <section> + <ul> + <li>:nth-child()</li> + <li>:nth-last-child() (wie child, zählt aber vom Ende)</li> + <li>:nth-of-type()</li> + <li>:nth-last-of-type() (wie of-type, zählt aber vom Ende)</li> + </ul> + </section> + + <section> + <p>Es wird aufgefallen sein: <code>:nth-child()</code> sowie die anderen <code>:nth-*()</code> Varianten haben am Ende Runde Klammern, die diesen Selektor so aussehen lassen, als werde eine Funktion (oder ähnlich) aufgerufen.</p> + <p>Innerhalb der Klammer wird Angegeben in welchen Abständen die Elemente selektiert werden.</p> + </section> + + <section> + <p>Beispiel-"Grid", jede einzelne Box hat die Klasse "child", der Parent-Container hat die Klasse "flex"</p> + <NthBox amount={5} /> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + // Selektiere das 2. Element mit der Klasse "child" + .child:nth-child(2) { + background-color: #E58F65; + } + + // Alternative Schreibweise mit "of"-Keyword + // (diesmal das 4. Kind) + :nth-child(4 of .child) { + background-color: #E58F65; + } + </code></pre> + </section> + + <section class="apply-styles pseudo"> + <p>Jetzt sind alle geraden Kind-Elemente "selektiert"</p> + <div class="container fourth"> + <NthBox amount={5} /> + </div> + </section> + + <section> + <p>Aber das geht auch einfacher:</p> + <pre class="css"><code data-trim data-line-numbers is:raw> + // Selektiert alle gerad-zahligen Vorkommnisse von "child" + :nth-child(even of .child) { + background-color: #E58F65 + } + + // Selektiert alle ungerad-zahligen Vorkommnisse von "child" + :nth-child(odd of .child) { + background-color: rgb(126, 154, 240); + } + </code></pre> + </section> + + <section class="apply-styles pseudo"> + <div class="container fifth"> + <NthBox amount={5} /> + </div> + </section> + + <section> + <p>Nun etwas Mathe</p> + <p>der <code>nth</code>-Selektor lässt auch eine Formel zu:</p> + <p><code>An+B</code>, dabei ist <code>n</code> "gedanklich" eine natürliche Zahl</p> + </section> + + <section> + <p>Beispiele:</p> + <hr> + <p><code>:nth-child(2n)</code> <br>- Selektiert jedes 2. Element (even)</p> + <hr> + <p><code>:nth-child(2n + 1)</code> <br>- Selektiert jedes 2. Element, beginnend ab dem 1. Element (odd)</p> + <hr> + <p><code>(n+7)</code> <br>- Selektiert das 7. und alle darauffolgenden Elemente</p> + <hr> + <p><code>(-n+3)</code> <br>- Selektiert die ersten drei Elemente</p> + </section> + + <section> + <h3>Ein <code>before & after</code></h3> + </section> + + <section> + <p>Jedes Element hat 2 Pseudo-Elemente die zusätzliches Styling für dieses Element zulassen.</p> + <p>Diese Pseudeo Elemente befinden sich "vor" und "nach" dem eigentlichen Element und werden mit <code>::before</code> und <code>::after</code> selektiert und modifiziert.</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + .before-and-after::before { + content: '>>before<<'; + background-color: rgb(255, 255, 172); + } + + .before-and-after::after { + content: '>>after<<'; + background-color: rgb(255, 194, 201); + } + </code></pre> + </section> + + <section class="apply-styles pseudo"> + <p>Beispiel</p> + <div class="container sixth"> + <span class="before-and-after"> + Ich bin nicht alleine... + </span> + </div> + </section> + + <section> + <p>Der Text in <code>content</code> wird entsprechend angezeigt, dies ist aber nicht der einzige Use-Case.</p> + <p>Tools wie <a href="https://cssarrowplease.com" target="_blank" rel="noopener noreferrer">CSS Arrow Please!</a> nutzen before und after, um z.B. eine "Sprechblase" zu erstellen</p> + </section> + + <section class="apply-styles pseudo"> + <div class="container seventh"> + <div class="arrow-box"> + CSS Arrow Please! + </div> + </div> + </section> + + <section> + <h3>Aktivierter Zustand mit <code>:active</code></h3> + </section> + + <section> + <p>Es gibt paar Pseudo-Klassen die einen Interaktiven Zustand von bestimmten Elementen stylen</p> + <p>Die erste Pseudo-Klasse dieser Art ist <code>:active</code>. Dieser Zustand wird für <code>button</code> und <code>a</code> Elemente verwendet.</p> + <p>Der "active" Zustand herrscht typischerweise, solange der Nutzer die (Primäre) Maustaste gedrückt hält.</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers="1-14|16-19" is:raw> + button { + padding: 1rem 2rem; + border: none; + outline: none; + background-color: white; + border: 4px solid black; + border-radius: 1rem; + font-size: xx-large; + cursor: pointer; + box-shadow: 24px 24px 0 black; + transition: + box-shadow 333ms ease-in-out, + transform 333ms ease-in-out; + } + + button:active { + box-shadow: 12px 12px 0 black; + transform: translateY(4px); + } + </code></pre> + </section> + + <section class="apply-styles pseudo"> + <div class="container eighth"> + <button>Drück mich!</button> + </div> + </section> + + <section> + <h3>Wenn der Mauszeiger über einem Element ist: <code>:hover</code></h3> + </section> + + <section> + <p>Mit <code>:hover</code> können wir auf den Zustand reagieren, wenn der Nutzer mit dem Mauszeiger über einem Element "schwebt".</p> + <p>Mit dieser Pseudo-Klasse lässt sich sehr schnell ein Interaktives Element für den Nutzer identifizieren.</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers="1-8|10-12" is:raw> + .card { + border: 4px solid black; + max-width: 300px; + padding: 2rem; + border-radius: 2rem; + box-shadow: 6px 6px 10px #0006; + transition: box-shadow 150ms ease-in-out; + } + + .card:hover { + box-shadow: 24px 24px 16px #0006; + } + </code></pre> + </section> + + <section class="apply-styles pseudo"> + <div class="container ninth"> + <div class="card"> + Hallo, ich bin eine "typische" Karte die einen Inhalt anzeigen soll! + </div> + </div> + </section> + + <section> + <h3>Die Negierung von Selektoren mit <code>:not()</code></h3> + </section> + + <section> + <p><code>:not(...)</code> ist eine Pseudoklassen-Funktion. Innerhalb der Klassen kann ein CSS-Selektor beschrieben werden und die Selektion wird dadurch negiert</p> + <p>Nach der Idee "Selektiere alle Elemente die folgendes nicht haben..."</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + p:not(.important) { + background-color: #282; // Grün + color: white; + } + + p.important { + background-color: #822; // Rot + color: white; + } + </code></pre> + </section> + + <section class="apply-styles not"> + <p class="important">Ich bin <code>.important</code></p> + <p class="normal">Ich bin <code>.normal</code></p> + </section> + + <section> + <h3><code>:where() & :is()</code></h3> + </section> + + <section> + <p>Folgendes Szenario</p> + </section> + + <section> + <pre class="html"><code data-trim data-line-numbers> + <ol> + <li>Level 1 - Item 1</li> + <li><ul> + <li>Level 2 - Item 1</li> + <li>Level 2 - Item 2</li> + <li> + <ol> + <li>Level 3 - Item 1</li> + </ol> + </li> + </ul></li> + </ol> + </code></pre> + </section> + + <section> + <ol> + <li>Level 1 - Item 1</li> + <li><ul> + <li>Level 2 - Item 1</li> + <li>Level 2 - Item 2</li> + <li> + <ol> + <li>Level 3 - Item 1</li> + </ol> + </li> + </ul></li> + </ol> + </section> + + <section> + <p>Wir haben also ineinander verschachtelte Listen (mit unterschiedlichen Listen-Typen)</p> + <p>Nehmen wir nun an, dass es auch sein kann, dass wir nicht sicher sein können ob die "Reihenfolge" der Listentypen immer gleich sein wird</p> + <p>Wie müssten CSS-Styles aussehen, um alle Fälle abdecken zu können?</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + ul,ol {...} // Level 1 Styles + ul,ol ul {...} // Level 2 Styles + ul,ol ol {...} // Level 2 Styles + ul,ol ul ul {...} // Level 3 Styles + ul,ol ul ol {...} // Level 3 Styles + ul,ol ol ul {...} // Level 3 Styles + ul,ol ol ol {...} // Level 3 Styles + </code></pre> + </section> + + <section class="apply-styles not-where"> + <ol> + <li>Level 1 - Item 1</li> + <li><ul> + <li>Level 2 - Item 1</li> + <li>Level 2 - Item 2</li> + <li> + <ol> + <li>Level 3 - Item 1</li> + </ol> + </li> + </ul></li> + </ol> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + :where(ul, ol) {} // Level 1 Styles + :where(ul, ol) :where(ul, ol) {} // Level 2 Styles + :where(ul, ol) :where(ul, ol) :where(ul, ol) {} // Level 3 Styles + </code></pre> + </section> + + <section class="apply-styles where"> + <ol> + <li>Level 1 - Item 1</li> + <li><ul> + <li>Level 2 - Item 1</li> + <li>Level 2 - Item 2</li> + <li> + <ol> + <li>Level 3 - Item 1</li> + </ol> + </li> + </ul></li> + </ol> + </section> + + <section> + <p>Welche Schlüsse ziehen wir hieraus?</p> + <ol> + <li>Lange, komplexe (geschachtelte) Queries benötigen viele "Iterationen"</li> + <li>Die Erweiterbarkeit kann darunter leiden</li> + <li>Grund für viele Bugs in Bezug auf CSS-Stylings</li> + </ol> + </section> + + <section> + <p><code>:where & :is</code> verhalten sich nach außen gleich. Wir können eine Komma-separierte Liste an CSS-Selektoren hinein kippen, wenn einer davon "matched" reicht das aus um die Stylings anzuwenden.</p> + </section> + + <section> + <p>Wo sind dann die Unterschieden zwischen <code>where & is</code>?</p> + </section> + + <section> + Matches mit <code>where</code>, zählen nicht zur "Spezifität" des selektierten Elementes, <code>is</code> zählt die am besten passende Spezifität. + </section> + + <section> + <pre class="html"><code data-trim data-line-numbers> + <p class="test">Hier steht ein Text!</p> + </code></pre> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + p:where(.test) { + background-color: black; + } + + p { + background-color: #002; + color: white; + + } + </code></pre> + </section> + + <section class="apply-styles where-specifity"> + <p class="test">Hier steht ein Text!</p> + </section> + + <section> + <pre class="css"><code data-trim data-line-numbers is:raw> + p:is(.test) { + background-color: white; + color: black; + } + + p { + background-color: #002; + color: white; + } + </code></pre> + </section> + + <section class="apply-styles is-specifity"> + <p class="test">Hier steht ein Text!</p> + </section> +</section> \ No newline at end of file diff --git a/src/components/slides/css-selectors-advanced/title.astro b/src/components/slides/css-selectors-advanced/title.astro new file mode 100644 index 0000000..87d2f17 --- /dev/null +++ b/src/components/slides/css-selectors-advanced/title.astro @@ -0,0 +1,3 @@ +<section> + <h1>CSS Selektoren - Erweitert</h1> +</section> \ No newline at end of file diff --git a/src/pages/slides/css-selectors-advanced.astro b/src/pages/slides/css-selectors-advanced.astro new file mode 100644 index 0000000..2b81dc5 --- /dev/null +++ b/src/pages/slides/css-selectors-advanced.astro @@ -0,0 +1,8 @@ +--- +import Reveal from "../../layouts/Reveal.astro"; +import Slides from '../../components/slides/css-selectors-advanced/index.astro'; +--- + +<Reveal title="CSS Selectors, Teil 2"> + <Slides /> +</Reveal> \ No newline at end of file