Warum bevorzugen wir CSS (- Variable) gegenüber SASS ($ Variable)?

Seit der Veröffentlichung des CodyHouse Framework vor einigen Monaten haben uns viele Benutzer gefragt, warum wir CSS-Variablen anstelle von SASS-Variablen ausgewählt haben, obwohl wir in dieser Umgebung SASS verwenden. In diesem Artikel werde ich über die Vorteile der Verwendung benutzerdefinierter Eigenschaften sprechen und darüber, warum sie für unseren Workflow von entscheidender Bedeutung sind.



Definition von Variablen


In diesem Artikel gehe ich davon aus, dass Sie mit den Grundlagen der benutzerdefinierten CSS- und SASS-Eigenschaften (oder eines anderen CSS-Präprozessors) vertraut sind. Wenn nicht, beginnen wir mit einem einfachen Beispiel:

In SCSS:

$color-primary: hsl(220, 90%, 56%); .link { color: $color-primary; } 

In CSS:

 :root { --color-primary: hsl(220, 90%, 56%); } .link { color: var(--color-primary); } 

Mit benutzerdefinierten Eigenschaften können Sie Variablen definieren, ohne dass CSS-Erweiterungen erforderlich sind (d. H. Sie müssen kein SASS verwenden).

Sind sie gleich? In der Tat nein! Im Gegensatz zu SASS-Variablen sind die Benutzereigenschaften 1) auf das Element beschränkt, für das sie deklariert sind, 2) eine Kaskade, 3) sie können in JavaScript gesteuert werden. Diese drei Funktionen eröffnen eine ganze Welt neuer Möglichkeiten. Lassen Sie mich Ihnen einige praktische Beispiele zeigen!

Erstellen und Anwenden von Farbthemen


Hier ist ein Beispiel, wie Sie mit SASS-Variablen zwei (vereinfachte) Farbthemen erstellen können:

 $color-primary: blue; $color-text: black; $color-bg: white; /*  */ $color-primary-invert: red; $color-text-invert: white; $color-bg-invert: black; .component { color: $color-text; background-color: $color-bg; a { color: $color-primary; } } .component--dark { color: $color-text-invert; background-color: $color-bg-invert; a { color: $color-primary-invert; } } 

Im obigen Beispiel haben wir ein "Standard" -Thema und ein "dunkles" Thema, in denen wir die Farben für Hintergrund und Text invertieren. Beachten Sie, dass wir in einem dunklen Thema jede Eigenschaft, die Farbvariablen verwendet hat, durchgehen und mit einer neuen Variablen aktualisieren müssen.

Solange wir uns an vereinfachte (unrealistische) Beispiele halten, treten keine Probleme auf. Aber was ist, wenn wir eine Komponente mit vielen Elementen haben? Wir müssten alle Eigenschaften, in denen Farbvariablen verwendet werden, neu schreiben und die Variablen durch neue ersetzen. Wenn Sie die Hauptkomponente ändern, sollten Sie alle Modifikatoren überprüfen. Ja ... nicht so bequem!

Bei der Erstellung unseres Frameworks haben wir einen anderen Ansatz entwickelt, der auf CSS-Variablen basiert. Definieren wir zunächst Variablen für Farbe:

 :root, [data-theme="default"] { --color-primary: blue; /*   */ --color-bg: white; --color-contrast-lower: hsl(0, 0%, 95%); --color-contrast-low: hsl(240, 1%, 83%); --color-contrast-medium: hsl(240, 1%, 48%); --color-contrast-high: hsl(240, 4%, 20%); --color-contrast-higher: black; } [data-theme] { background-color: var(--color-bg); color: var(--color-contrast-high); } [data-theme="dark"] { --color-primary: red; /*   */ --color-bg: black; --color-contrast-lower: hsl(240, 6%, 15%); --color-contrast-low: hsl(252, 4%, 25%); --color-contrast-medium: hsl(240, 1%, 57%); --color-contrast-high: hsl(0, 0%, 89%); --color-contrast-higher: white; } 

Hinweis: Im obigen Beispiel verwenden wir die data- * -Attribute, um das Farbthema anzuwenden. Dies hat jedoch nichts mit CSS-Variablen und SASS-Variablen zu tun. Zusätzlich haben wir eine Skala neutraler Werte unter Verwendung der Nomenklatur basierend auf dem „Kontrastniveau“ definiert.

Der wichtige Punkt ist, dass wir für unser zweites, drittes, viertes ... (dunkles) Thema keine neuen Farbvariablen erstellen müssen. Im Gegensatz zu SASS können wir den Wert vorhandener benutzerdefinierter Eigenschaften überschreiben.

So wenden Sie Farbvariablen auf eine Komponente an:

 .component { color: var(--color-contrast-higher); background-color: var(--color-bg); border-bottom: 1px solid var(--color-contrast-low); a { color: var(--color-primary); } } 

Was ist mit der dunklen Version der Komponente? Wir brauchen kein zusätzliches CSS. Da wir Variablen neu definieren und nicht ersetzen, müssen wir die richtigen Variablen für die Farbe nur beim ersten Erstellen der Komponente anwenden. Es spielt keine Rolle, wie kompliziert die Komponente wird, nachdem Sie die Farbthemen in der Datei _colors.scss festgelegt und die Farbvariablen auf die Elemente Ihrer Komponenten angewendet haben .

Sie können Farbthemen auf sehr einfache Weise anwenden:

 <section data-theme="dark"> <div class="component"> <div class="child" data-theme="default"></div> </div> </section> 

Im obigen Beispiel haben wir dem Abschnitt ein dunkles Thema und dem Element .child ein Standardthema zugewiesen. Richtig, Sie können in Farbthemen investieren!

Dies wird durch die Verwendung von CSS-Eigenschaften ermöglicht. Was es möglich machte, so interessante Dinge wie diese in kürzester Zeit zu tun.



Hier sind einige Links, wenn Sie mehr über das Verwalten von Farben mit dem CodyHouse-Framework erfahren möchten:


Verwaltung von Schriftarten


Eine modulare Skala besteht aus einer Reihe harmonischer (dimensionaler) Werte, die für typografische Elemente gelten. So können Sie die Schriftgröße in SCSS mithilfe von SASS-Variablen festlegen:

 $text-xs: 0.694em; $text-sm: 0.833em; $text-base-size: 1em; $text-md: 1.2em; $text-lg: 1.44em; $text-xl: 1.728em; 

Ein Standardansatz wäre, eine Schriftskala mit einem Drittanbieter-Tool zu erstellen (oder mathematische Operationen auszuführen) und die Werte dann wie im obigen Beispiel in Ihren Stil zu importieren.

Bei der Erstellung des Frameworks haben wir beschlossen, die gesamte Skalierungsformel in die Datei _typography.scss aufzunehmen. So legen wir die Schriftgröße mithilfe von CSS-Variablen fest:

 :root { //    --text-base-size: 1em; //   --text-scale-ratio: 1.2; --text-xs: calc((1em / var(--text-scale-ratio)) / var(--text-scale-ratio)); --text-sm: calc(var(--text-xs) * var(--text-scale-ratio)); --text-md: calc(var(--text-sm) * var(--text-scale-ratio) * var(--text-scale-ratio)); --text-lg: calc(var(--text-md) * var(--text-scale-ratio)); --text-xl: calc(var(--text-lg) * var(--text-scale-ratio)); --text-xxl: calc(var(--text-xl) * var(--text-scale-ratio)); --text-xxxl: calc(var(--text-xxl) * var(--text-scale-ratio)); } 

Was ist der Vorteil dieses Ansatzes? Dies ermöglicht die Steuerung des gesamten Drucksystems durch Bearbeiten von nur zwei Variablen: --text-base-size (Größe der Basisschrift) und --text-scale-ratio (Skalierungsfaktor).

"Kannst du nicht dasselbe mit Sass-Variablen machen?" Nicht, wenn Sie die Typografie an bestimmten Stellen in Medienabfragen ändern möchten:

 :root { @include breakpoint(md) { --text-base-size: 1.25em; --text-scale-ratio: 1.25; } } 

Dieses Stück ist der Eckpfeiler unseres flexiblen Ansatzes. Da wir relative Ems-Einheiten verwenden, wirkt sich dies beim Ändern der --text-base-size (der Größe der Basisschrift) sowohl auf die Typografie als auch auf den Abstand aus. Als Ergebnis erhalten Sie ein System, das die Größe aller Ihrer Komponenten ändert, ohne dass Medienabfragen auf Komponentenebene festgelegt werden müssen.



Hier sind einige nützliche Links:


Entfernungsskalensteuerung


Die Intervallskala entspricht der Typenskala, gilt jedoch für räumliche Werte. Die Aufnahme der Skalenformel in die Struktur ermöglichte es uns erneut, das Intervallsystem zu steuern und darauf zu reagieren:

 :root { --space-unit: 1em; --space-xxxxs: calc(0.125 * var(--space-unit)); --space-xxxs: calc(0.25 * var(--space-unit)); --space-xxs: calc(0.375 * var(--space-unit)); --space-xs: calc(0.5 * var(--space-unit)); --space-sm: calc(0.75 * var(--space-unit)); --space-md: calc(1.25 * var(--space-unit)); --space-lg: calc(2 * var(--space-unit)); --space-xl: calc(3.25 * var(--space-unit)); --space-xxl: calc(5.25 * var(--space-unit)); --space-xxxl: calc(8.5 * var(--space-unit)); --space-xxxxl: calc(13.75 * var(--space-unit)); } @supports(--css: variables) { :root { @include breakpoint(md) { --space-unit: 1.25em; } } } 

Dieser Ansatz wird in Kombination mit der oben diskutierten Typografiemethode besonders leistungsfähig. Mit nur wenigen Zeilen CSS erhalten Sie reaktionsschnelle Komponenten:



Eine andere Sache, die ich an der Verwendung von Ems-Modulen mit diesem Abstandssystem mag, ist, dass Abstand und Typografiegröße, wenn sie an einem bestimmten Punkt in einer Medienabfrage richtig aussehen, mit ziemlicher Sicherheit an allen Punkten der Medienabfrage richtig aussehen, unabhängig davon dass Sie den Wert --space-unit aktualisieren . Daher kann ich entwerfen, ohne die Größe der Browserfenster ändern zu müssen (es sei denn, ich möchte das Verhalten der Komponente ändern).

Weitere verwandte Links:


Bearbeiten des „vertikalen Rhythmus“ auf Komponentenebene


Im Gegensatz zur SASS-Variablen können wir den Wert von CSS-Variablen überschreiben. Eine Möglichkeit, diese Eigenschaft zu verwenden, besteht darin, anderen benutzerdefinierten Eigenschaften benutzerdefinierte Eigenschaften hinzuzufügen und so „Steuerelemente“ zu erstellen, die Sie auf Komponentenebene bearbeiten können.

In diesem Beispiel möchten Sie beim Festlegen des vertikalen Abstands für eine Textkomponente wahrscheinlich die Zeilenhöhe und den Rand unten für Ihre Elemente angeben:

 .article { h1, h2, h3, h4 { line-height: 1.2; margin-bottom: $space-xs; } ul, ol, p, blockquote { line-height: 1.5; margin-bottom: $space-md; } } 

Dieses Tempo hängt jedoch davon ab, wo der Text verwendet wird. Wenn Sie beispielsweise möchten, dass Ihr Text präziser ist, müssen Sie eine Komponentenvariante (Modifikator) erstellen, in der Sie verschiedene Werte der Intervalle anwenden:

 .article--sm { h1, h2, h3, h4 { line-height: 1.1; margin-bottom: $space-xxxs; } ul, ol, p, blockquote { line-height: 1.4; margin-bottom: $space-sm; } } 

... und so jedes Mal, wenn Sie den "vertikalen Rhythmus" aktualisieren möchten.

Hier ist ein alternativer Ansatz, der auf CSS-Variablen basiert:

 .text-component { --component-body-line-height: calc(var(--body-line-height) * var(--line-height-multiplier, 1)); --component-heading-line-height: calc(var(--heading-line-height) * var(--line-height-multiplier, 1)); --line-height-multiplier: 1; --text-vspace-multiplier: 1; h1, h2, h3, h4 { line-height: var(--component-heading-line-height); margin-bottom: calc(var(--space-xxxs) * var(--text-vspace-multiplier)); } h2, h3, h4 { margin-top: calc(var(--space-sm) * var(--text-vspace-multiplier)); } p, blockquote, ul li, ol li { line-height: var(--component-body-line-height); } ul, ol, p, blockquote, .text-component__block, .text-component__img { margin-bottom: calc(var(--space-sm) * var(--text-vspace-multiplier)); } } 

--line-height-multiplier und --text-vspace-multiplier sind zwei Steuervariablen für Textkomponenten . Wenn wir den Modifikator der .text-Komponentenklasse erstellen, müssen wir zum Bearbeiten des vertikalen Intervalls nur diese beiden Variablen neu definieren:

 .article.text-component { //     --line-height-multiplier: 1.13; //     --text-vspace-multiplier: 1.2; //    } 

Falls Sie es selbst ausprobieren möchten und beachten Sie:



Verhaltenskomponenten abstrahieren


Die Möglichkeit, den Wert einer Komponente zu überschreiben, kann auf verschiedene Arten verwendet werden. Im Allgemeinen erleichtern Sie jederzeit das Leben einer Komponente, wenn Sie das Verhalten einer Komponente in einer oder mehreren Variablen abstrahieren können, wenn diese Komponente bearbeitet werden muss (oder Sie eine Komponentenvariante erstellen müssen).

Ein Beispiel ist unsere Komponente "Automatisches Raster" , bei der wir ein CSS-Raster verwenden, um ein Layout zu erstellen. Dabei füllen Galerieelemente automatisch den verfügbaren Platz basierend auf der in CSS angegebenen Mindestbreite aus. Anschließend abstrahieren wir die Mindestbreite der Elemente und speichern sie in einer Variablen.


Der Mindestbreitenwert ist das einzige, was Sie ändern müssen, wenn Sie die Option Rasterkomponente für automatische Größe erstellen.

Was ist der Haken?


Kurz gesagt: Browserunterstützung ... Mit dem PostCss- Plugin können Sie CSS-Variablen auf alle in diesem Artikel beschriebenen Arten verwenden. Für ältere Browser gibt es eine Reihe von Einschränkungen (<IE11). Ansonsten ist es kostenlos zu benutzen. Weitere Informationen zu den Einschränkungen bei der Verwendung von CSS-Variablen finden Sie in unserer Dokumentation .

Kann ich CSS-Variablen mit einem Präprozessor verwenden?


Ja! Während SASS (oder ein anderer Präprozessor) es Ihnen ermöglicht, das zu tun, was Sie in CSS nicht können, und Sie es brauchen, warum nicht? SASS ist keine Bibliothek, die Benutzer herunterladen müssen, wenn sie auf Ihre Site zugreifen. Dies ist ein Werkzeug in Ihrem Workflow. Wir verwenden SASS zum Beispiel, um Farbfunktionen zu definieren , die mit CSS-Variablen arbeiten.

Fazit


In diesem Artikel haben wir uns einige Beispiele angesehen, die den Vorteil der Verwendung von CSS-Variablen gegenüber SASS-Variablen demonstrieren. Wir haben uns darauf konzentriert, wie Sie damit Steuerelemente erstellen können, die das Ändern von Komponenten beschleunigen oder Regeln festlegen, die sich auf Typografie und Intervalle auswirken. Wir haben viel darüber nachgedacht, und ich hoffe, dass Sie aus diesem Beitrag etwas lernen und es in Ihrer Arbeit verwenden können.

Source: https://habr.com/ru/post/de456302/


All Articles