CSS Organisation
Wie du bei 2000+ Zeilen CSS nicht den Verstand verlierst.
Das Problem mit wachsendem CSS
Kennst du das? Du startest ein Projekt mit einer übersichtlichen style.css. Nach
ein
paar Wochen sind es 500 Zeilen. Nach ein paar Monaten 2000. Irgendwann scrollst du mehr als
du
codest, und ⌘ / Strg + F wird dein bester Freund.
Mir jedenfalls geht es so. Gerade bei diesem Projekt habe ich regelrecht mit Klassen um mich geworfen - hier ein Code-Snippet, da ein Beispiel gestyled... Ich habe mich schön im CSS ausgetobt, und irgendwann kommt der Moment, wo du sagst: „Moment mal, das hatte ich doch schon mal irgendwo?" Also habe ich einfach meinen digitalen Freund gefragt: „Wie zum ... behalten andere da noch den Überblick?!"
Die gute Nachricht: Du bist nicht allein. Die schlechte: Es gibt keine magische Lösung. Aber es gibt bewährte Strategien, die das Chaos bändigen. Welche davon zu dir passt, hängt von deinem Projekt, deinem Team und deinen Vorlieben ab.
Die meisten Entwickler kämpfen genauso - oder sie haben gelernt, das Problem zu vermeiden, bevor es entsteht.
Methode 1: Aufteilen in mehrere Dateien
Der natürlichste erste Schritt: Statt alles in eine riesige Datei zu packen, verteilst du dein CSS auf mehrere kleinere Dateien. Das ist wie Schubladen in einem Schrank - du weißt sofort, wo du suchen musst.
Das ist eigentlich schon der Weg, den ich gewählt habe, nur bei weitem nicht so "radikal".
Typische Ordnerstruktur
css/
├── base/
│ ├── reset.css /* Browser-Reset oder Normalize */
│ ├── typography.css /* Schriften, Überschriften, Text */
│ └── variables.css /* Custom Properties */
├── components/
│ ├── buttons.css /* Alle Button-Styles */
│ ├── cards.css /* Karten-Komponenten */
│ ├── navigation.css /* Haupt- und Sub-Navigation */
│ └── forms.css /* Formulare und Inputs */
├── layout/
│ ├── header.css /* Header-spezifische Styles */
│ ├── footer.css /* Footer-Styles */
│ └── grid.css /* Layout-Grid, Container */
├── pages/
│ ├── home.css /* Nur für Startseite */
│ └── contact.css /* Nur für Kontaktseite */
├── utilities/
│ └── utilities.css /* Helper-Klassen: .mt-xl, .text-center */
└── main.css /* Importiert alles */
Alles zusammenführen
In deiner main.css oder style.css importierst du dann alles -
diesen
Schritt habe ich aktuell noch vor mir.
/* main.css */
@import 'base/variables.css';
@import 'base/reset.css';
@import 'base/typography.css';
@import 'layout/grid.css';
@import 'layout/header.css';
@import 'layout/footer.css';
@import 'components/buttons.css';
@import 'components/cards.css';
@import 'components/navigation.css';
@import 'components/forms.css';
@import 'pages/home.css';
@import 'utilities/utilities.css';
Die Reihenfolge der Imports ist entscheidend! CSS wird von oben
nach unten gelesen. variables.css muss ganz oben stehen,
utilities.css ganz unten, damit Utility-Klassen alles überschreiben können.
Warum die Reihenfolge wichtig ist: CSS Spezifität
Die Spezifität bestimmt, welche CSS-Regel gewinnt, wenn mehrere Regeln auf dasselbe Element zutreffen. Sie wird als Punktesystem berechnet:
- Inline-Styles
style="..."= 1-0-0-0 (Nicht sicher, bitte vermeiden!) - IDs
#header= 0-1-0-0 - Klassen, Pseudo-Klassen, Attribute
.nav,:hover,[type="text"]= 0-0-1-0 - Elemente, Pseudo-Elemente
div,::before= 0-0-0-1
Beispiel-Vergleich
main ul:not(.arrow-list) li
Spezifität: 0-1-3
- 0 IDs
- 1 Klasse (durch
:not(.arrow-list)) - 3 Elemente (
main,ul,li)
.cheatsheet-grid .cheatsheet-section ul li
Spezifität: 0-2-2
- 0 IDs
- 2 Klassen (
.cheatsheet-grid,.cheatsheet-section) - 2 Elemente (
ul,li)
Ergebnis: Die zweite Regel gewinnt, weil Klassen (0-2-2) schwerer wiegen als Elemente (0-1-3).
Dann gewinnt die Regel, die später im CSS steht - die sogenannte
Cascade. Genau deshalb muss utilities.css als letztes importiert
werden: Ihre Klassen sollen alles andere überschreiben können.
Die At-Rules
Das @ leitet sogenannte At-Rules ein - spezielle Anweisungen an den Browser,
die
keine normalen Style-Regeln sind.
| At-Rule | Was sie tut |
|---|---|
@import |
Lädt eine andere CSS-Datei |
@font-face |
Definiert eine eigene Schriftart |
@media |
Styles nur unter bestimmten Bedingungen (Responsive!) |
@keyframes |
Definiert Animationsschritte |
@supports |
Styles nur wenn Browser ein Feature unterstützt |
@layer |
Gruppiert CSS in Ebenen (neu, sehr mächtig!) |
Warum das @ ?
Es signalisiert dem Browser: "Achtung, das ist keine normale Selektor-Regel, sondern eine
Meta-Anweisung." Das @ trennt sozusagen die "Verwaltung" vom eigentlichen
Styling.
Ist also keine Funktion im Programmier-Sinne, sondern eher wie ein Präfix für "Sonderbefehle".
Vor- & Nachteile dieser Methode
- Einfach umzusetzen - keine neuen Tools nötig
- Klare Trennung nach Funktion
- Einzelne Dateien bleiben überschaubar
- Weniger
<link>imhead - Funktioniert mit jedem Projekt
- Mehr HTTP-Requests (ohne Build-Prozess)
@importin CSS - Sequentielles Laden (langsamer)- Ohne Konventionen kann es trotzdem chaotisch werden
- Namenskonflikte sind weiterhin möglich
Methode 2: BEM - Block Element Modifier
BEM ist eine Namenskonvention für CSS-Klassen. Die Idee: Der Klassenname selbst verrät dir, was das Element ist und wozu es gehört. Keine Rätselraten, keine tiefen Verschachtelungen.
Die drei Bausteine
- Block: Ein eigenständiger Komponente
.card,.navigation - Element: Ein Teil des Blocks, der ohne ihn keinen Sinn ergibt
.card__title,.card__image - Modifier: Eine Variation des Blocks oder Elements
.card--featured,.button--large
Die Syntax
/* Block */
.card { }
/* Element (mit doppeltem Unterstrich) */
.card__title { }
.card__image { }
.card__content { }
.card__button { }
/* Modifier (mit doppeltem Bindestrich) */
.card--featured { }
.card--dark { }
.card__button--primary { }
.card__button--disabled { }
Zunächst wird die Basis .card gestyled. Die Elemente innerhalb der
.card werden mit __ erweitert, z. B. .card__button.
Soll
der Button mehrere Zustände haben können, werden die Elemente modifiziert und mit
-- erweitert, z. B. .card__button--disabled.
Häufiger Denkfehler: Man könnte meinen, dass beim Button
.card__button--disabled allein reicht. Aber dann fehlen alle Basis-Styles! Der
Modifier ist nur
die Abweichung vom Standard. Im HTML brauchst du deshalb immer beide
Klassen:
<article class="card card--featured">
<img class="card__image" src="..." alt="...">
<h3 class="card__title">Überschrift</h3>
<p class="card__content">Beschreibung...</p>
<button class="card__button card__button--primary"> /* beide Klassen*/
Mehr erfahren
</button>
</article>
Warum das funktioniert
BEM löst mehrere Probleme gleichzeitig:
- Flache Spezifität: Keine verschachtelten Selektoren wie
.header .nav .nav-list .nav-item a. Alles hat die gleiche Spezifität (eine Klasse). - Selbstdokumentierend:
.card__titlesagt dir sofort: "Das ist der Titel innerhalb einer Card." - Keine Namenskonflikte:
.card__titleund.article__titlesind eindeutig unterschiedlich. - Einfach zu suchen: Du suchst nach
.cardund findest alles, was zur Card gehört.
Vor- & Nachteile dieser Methode
- Extrem flache Spezifität - keine Spezifitäts-Kriege
- Klassennamen sind selbsterklärend
- Funktioniert mit jedem Tech-Stack
- Weit verbreitet - viele Entwickler kennen es
- Lange Klassennamen im HTML
- Anfangs ungewohnt zu schreiben
- Kann bei sehr tiefen Verschachtelungen sperrig werden
Du musst nicht dogmatisch sein. Viele Teams nutzen BEM nur für Komponenten, nicht für Layout oder Utilities.
Methode 3: ITCSS - Inverted Triangle CSS
ITCSS ist eine Architektur-Methode von Harry Roberts. Die Idee: Du sortierst dein CSS nach Reichweite und Spezifität - von breit und generisch zu eng und spezifisch.
Das umgekehrte Dreieck
Stell dir ein auf den Kopf gestelltes Dreieck vor:
Die sieben Schichten erklärt
1. Settings
Globale Variablen, die überall verwendet werden:
/* _settings.css */
:root {
--color-primary: #2a7ae2;
--color-text: #1a1a1a;
--font-base: 'Fira Code', monospace;
--spacing-unit: 8px;
}
2. Tools
Mixins und Funktionen (relevant bei Sass/SCSS):
/* _tools.scss (Sass) */
@mixin respond-to($breakpoint) {
@media (min-width: $breakpoint) {
@content;
}
}
3. Generic
Reset, Normalize, Box-Sizing - Styles ohne Klassen:
/* _generic.css */
*, *::before, *::after {
box-sizing: border-box;
}
body {
margin: 0;
padding: 0;
}
4. Elements
Basis-Styles für HTML-Elemente (keine Klassen):
/* _elements.css */
h1, h2, h3 {
font-family: var(--font-heading);
line-height: 1.2;
}
a {
color: var(--color-primary);
}
5. Objects
Layout-Patterns, ungestylt (OOCSS-Prinzip):
/* _objects.css */
.o-container {
max-width: 1200px;
margin-inline: auto;
padding-inline: 1rem;
}
.o-grid {
display: grid;
gap: var(--spacing-unit);
}
6. Components
Die eigentlichen UI-Komponenten:
/* _components.css */
.c-button {
padding: 0.75em 1.5em;
background: var(--color-primary);
border: none;
border-radius: 4px;
}
.c-card {
background: white;
border-radius: 8px;
box-shadow: 0 2px 8px rgba(0,0,0,0.1);
}
7. Utilities
Helper-Klassen mit !important (ja, hier ist es erlaubt!):
/* _utilities.css */
.u-hidden {
display: none !important;
}
.u-text-center {
text-align: center !important;
}
.u-mt-xl {
margin-top: 3rem !important;
}
Vor- & Nachteile dieser Methode
- Spezifität steigt natürlich - weniger Konflikte
- Klare Struktur für große Teams
- Kombinierbar mit BEM für Komponenten
- Skaliert gut bei wachsenden Projekten
- Lernkurve - man muss die Philosophie verstehen
- Kann für kleine Projekte übertrieben sein
- Namenskonventionen (o-, c-, u-) sind optional, aber hilfreich
Methode 4: Sass/SCSS - Der Klassiker unter den Preprocessors
Sass (Syntactically Awesome Style Sheets) erweitert CSS um Features, die dir das Leben leichter machen: Variablen, Verschachtelung, Mixins, Funktionen und mehr.
Sass hat zwei Syntaxen. Die ältere .sass nutzt
Einrückungen statt Klammern. Die neuere .scss sieht aus wie normales CSS
mit
Extras. Die meisten nutzen heute SCSS.
Verschachtelung (Nesting)
Statt flacher CSS-Selektoren kannst du verschachteln:
/* _navigation.scss */
.nav {
display: flex;
gap: 1rem;
&__list {
list-style: none;
margin: 0;
padding: 0;
}
&__item {
position: relative;
&:hover {
.nav__dropdown {
display: block;
}
}
}
&__link {
color: var(--color-text);
text-decoration: none;
&:hover {
color: var(--color-primary);
}
&--active {
font-weight: bold;
}
}
}
Das & steht für den Parent-Selector. &__list wird zu
.nav__list.
Variablen
/* _variables.scss */
$color-primary: #2a7ae2;
$color-secondary: #e74c3c;
$font-stack: 'Fira Code', monospace;
$breakpoint-md: 768px;
/* Verwendung */
.button {
background: $color-primary;
font-family: $font-stack;
@media (min-width: $breakpoint-md) {
padding: 1rem 2rem;
}
}
Sass-Variablen werden beim Kompilieren ersetzt - sie existieren nicht im Browser. CSS
Custom
Properties --color-primary sind zur Laufzeit verfügbar und können z.B. für
Dark
Mode geändert werden. Beide haben ihre Berechtigung!
Mixins - Wiederverwendbare Codeblöcke
/* _mixins.scss */
@mixin flex-center {
display: flex;
justify-content: center;
align-items: center;
}
@mixin respond-to($breakpoint) {
@media (min-width: $breakpoint) {
@content;
}
}
/* Verwendung */
.hero {
@include flex-center;
min-height: 100vh;
@include respond-to(768px) {
padding: 4rem;
}
}
Partials und Import
Dateien mit _ am Anfang sind "Partials" - sie werden nicht einzeln kompiliert:
scss/
├── abstracts/
│ ├── _variables.scss
│ ├── _mixins.scss
│ └── _functions.scss
├── base/
│ ├── _reset.scss
│ └── _typography.scss
├── components/
│ ├── _buttons.scss
│ └── _cards.scss
├── layout/
│ ├── _header.scss
│ └── _footer.scss
└── main.scss
/* main.scss */
@use 'abstracts/variables';
@use 'abstracts/mixins';
@use 'base/reset';
@use 'base/typography';
@use 'components/buttons';
@use 'components/cards';
@use 'layout/header';
@use 'layout/footer';
Hinweis: @import ist veraltet! Nutze stattdessen
@use und @forward. Sie haben besseres Scoping und vermeiden
Duplikate.
Der Build-Prozess
SCSS muss zu CSS kompiliert werden. Optionen:
- VS Code Extension: "Live Sass Compiler" - kompiliert beim Speichern
- npm:
npm install -g sass, dannsass --watch scss:css - Build-Tools: Webpack, Vite, Gulp - für komplexere Projekte
Vor- & Nachteile dieser Methode
- Mächtiger als reines CSS
- Bessere Organisation durch Partials
- Mixins reduzieren Wiederholungen
- Verschachtelung macht BEM angenehmer
- Riesige Community und Dokumentation
- Build-Schritt erforderlich
- Lernkurve für fortgeschrittene Features
- Zu tiefe Verschachtelung kann zu aufgeblähtem CSS führen
- Modernes CSS holt auf (Custom Properties, Nesting ist nativ in Arbeit)
Methode 5: CSS-in-JS und Scoped CSS
Bei JavaScript-Frameworks wie React, Vue oder Svelte gibt es einen anderen Ansatz: Das CSS lebt direkt bei der Komponente. Kein globales Stylesheet, keine Namenskonflikte.
Scoped CSS in Vue
Vue macht es besonders einfach:
<template>
<div class="card">
<h3 class="title">{{ title }}</h3>
<p class="content">{{ content }}</p>
</div>
</template>
<style scoped>
.card {
background: white;
border-radius: 8px;
padding: 1rem;
}
.title {
/* Nur DIESE .title Klasse - nicht global! */
font-size: 1.25rem;
margin-bottom: 0.5rem;
}
.content {
color: #666;
}
</style>
Das scoped Attribut sorgt dafür, dass Vue automatisch einzigartige Attribute
generiert. Im Browser wird daraus:
.card[data-v-7ba5bd90] { ... }
.title[data-v-7ba5bd90] { ... }
CSS-in-JS mit styled-components (React)
import styled from 'styled-components';
const Card = styled.div`
background: white;
border-radius: 8px;
padding: 1rem;
&:hover {
box-shadow: 0 4px 12px rgba(0,0,0,0.15);
}
`;
const Title = styled.h3`
font-size: 1.25rem;
margin-bottom: 0.5rem;
color: ${props => props.featured ? '#e74c3c' : '#1a1a1a'};
`;
// Verwendung
function MyCard({ title, content, featured }) {
return (
<Card>
<Title featured={featured}>{title}</Title>
<p>{content}</p>
</Card>
);
}
CSS Modules
Ein Mittelweg - normale CSS-Dateien, aber mit automatischem Scoping:
/* Card.module.css */
.card {
background: white;
border-radius: 8px;
}
.title {
font-size: 1.25rem;
}
// Card.jsx
import styles from './Card.module.css';
function Card({ title }) {
return (
<div className={styles.card}>
<h3 className={styles.title}>{title}</h3>
</div>
);
}
// Generiert: class="Card_card__x7Zk2"
Vor- & Nachteile dieser Methode
- Keine Namenskonflikte - per Design unmöglich
- CSS lebt direkt bei der Komponente
- Beim Löschen einer Komponente verschwindet auch das CSS
- Dynamische Styles basierend auf Props
- Nur mit JavaScript-Frameworks sinnvoll
- Build-Prozess erforderlich
- Globale Styles werden komplizierter
- Performance-Overhead bei CSS-in-JS (Runtime)
- Lernkurve für das jeweilige Tool
CSS-in-JS ist Overkill. Es glänzt in komplexen Web-Apps mit vielen wiederverwendbaren Komponenten.
Methode 6: Utility-First mit Tailwind CSS
Der radikalste Ansatz: Du schreibst kaum noch eigenes CSS. Stattdessen nutzt du vordefinierte Utility-Klassen direkt im HTML.
Traditionelles CSS vs. Utility-First
Traditionell:
<div class="card">
<h3 class="card-title">Titel</h3>
<p class="card-content">Inhalt...</p>
</div>
.card {
display: flex;
flex-direction: column;
gap: 1rem;
padding: 1.5rem;
background: #1a1a1a;
border-radius: 0.5rem;
}
.card-title {
font-size: 1.25rem;
font-weight: 600;
color: white;
}
.card-content {
color: #a0a0a0;
}
Mit Tailwind:
<div class="flex flex-col gap-4 p-6 bg-gray-900 rounded-lg">
<h3 class="text-xl font-semibold text-white">Titel</h3>
<p class="text-gray-400">Inhalt...</p>
</div>
Kein zusätzliches CSS nötig!
Das Tailwind-Vokabular
Einige häufige Klassen:
| Kategorie | Klassen | Bedeutung |
|---|---|---|
| Spacing | p-4, m-2, px-6, mt-8
|
Padding/Margin (4 = 1rem) |
| Flexbox | flex, items-center,
justify-between
|
Layout |
| Grid | grid, grid-cols-3, gap-4 |
Grid-Layout |
| Farben | bg-blue-500, text-white,
border-gray-300
|
Hintergrund, Text, Border |
| Typography | text-lg, font-bold,
leading-relaxed
|
Schriftgröße, -gewicht, Zeilenhöhe |
| Responsive | md:flex, lg:grid-cols-4 |
Ab Breakpoint aktiv |
| States | hover:bg-blue-600, focus:ring-2 |
Pseudo-Klassen |
| Dark Mode | dark:bg-gray-800, dark:text-white |
Nur im Dark Mode |
Responsive Design mit Tailwind
<div class="
grid
grid-cols-1
md:grid-cols-2
lg:grid-cols-4
gap-4
p-4
md:p-8
">
<!-- 1 Spalte mobil, 2 ab 768px, 4 ab 1024px -->
</div>
Komponenten extrahieren
Wenn sich Patterns wiederholen, kannst du sie in CSS extrahieren:
/* Mit @apply (in deiner CSS-Datei) */
.btn-primary {
@apply px-6 py-3 bg-blue-600 text-white font-semibold
rounded-lg hover:bg-blue-700 transition-colors;
}
Vor- & Nachteile dieser Methode
- Extrem schnelle Entwicklung
- Konsistentes Design-System eingebaut
- Keine CSS-Dateien die wachsen
- Unused CSS wird automatisch entfernt (PurgeCSS)
- Responsive Design ist trivial
- HTML wird "hässlich" mit vielen Klassen
- Lernkurve - du musst die Klassen kennen
- Build-Prozess erforderlich
- Nicht für jeden - polarisierender Ansatz
- Komplexe Custom-Styles werden umständlich
Tailwind ist großartig für schnelles Prototyping und wenn du das Design-System akzeptierst. Für individuelle Designs wie DevPanicZone, wo du volle Kontrolle willst, kann es einschränkend sein.
Tailwind ist großartig für schnelles Prototyping und wenn du das Design-System akzeptierst. Für individuelle Designs wie DevPanicZone, wo du volle Kontrolle willst, kann es einschränkend sein.
Bonus: CSS Layers (@layer)
CSS Layers sind eine native Browser-Lösung für das Spezifitäts-Problem. Sie ermöglichen dir, CSS in Ebenen zu organisieren, deren Reihenfolge du selbst bestimmst - unabhängig von der Position im Code.
/* Reihenfolge definieren: Letzte gewinnt bei Konflikten */
@layer reset, base, components, utilities;
/* Reset-Styles */
@layer reset {
*, *::before, *::after {
box-sizing: border-box;
margin: 0;
}
}
/* Basis-Styles */
@layer base {
body {
font-family: var(--font-base);
line-height: 1.6;
}
a {
color: var(--color-primary);
}
}
/* Komponenten */
@layer components {
.button {
padding: 0.75rem 1.5rem;
background: var(--color-primary);
border-radius: 4px;
}
}
/* Utilities überschreiben alles */
@layer utilities {
.hidden { display: none !important; }
.text-center { text-align: center; }
}
- Spezifität wird ignoriert: Ein Selektor in
utilitiesgewinnt gegencomponents, egal wie spezifisch - Reihenfolge im Code egal: Du kannst Layers überall definieren
- Kein Build-Prozess: Funktioniert nativ im Browser
- Browser-Support: Alle modernen Browser seit 2022 (Chrome 99+, Firefox 97+, Safari 15.4+)
Layers vs. ITCSS
CSS Layers sind quasi ITCSS nativ im Browser. Der Unterschied:
ITCSS
- Konvention - du musst dich dran halten
- Reihenfolge im Code entscheidend
- Funktioniert überall
@layer
- Browser erzwingt die Reihenfolge
- Reihenfolge im Code egal
- Braucht moderne Browser
Vergleich: Welche Methode passt zu dir?
| Methode | Lernkurve | Build-Tools | Projektgröße | Ideal für |
|---|---|---|---|---|
| Dateiaufteilung | ★ | Nein | Klein-Mittel | Einsteiger, einfache Projekte |
| BEM | ★★ | Nein | Alle | Teams, langlebige Projekte |
| ITCSS | ★★★ | Optional | Mittel-Groß | Enterprise, große Teams |
| Sass/SCSS | ★★ | Ja | Mittel-Groß | Komplexe Styles, DRY-Code |
| CSS-in-JS | ★★★ | Ja | Mittel-Groß | React/Vue/Svelte Apps |
| Tailwind | ★★ | Ja | Alle | Schnelles Prototyping, Teams |
| CSS Layers | ★★ | Nein | Alle | Moderne Browser, ITCSS-Alternative |
Beispiel: Mein Projekt
Basierend auf dem, was ich bereits habe und wo ich hin will.
Kurzfristig: Dateiaufteilung erweitern: check
Meine Basis mit getrennten Dateien ist bereits übersichtlich.
css/
├── style.css /* Nur noch: Reset, Typography, Base */
├── layout.css /* Header, Footer, Grid, Container */
├── components.css /* Buttons, Cards, Info-Boxes */
├── tutorials.css /* Bleibt: Tutorial-spezifische Styles */
├── sidebar.css /* Bleibt */
└── utilities.css /* Bleibt */
Mittelfristig: BEM für neue Komponenten
Wenn ich neue Komponenten brauche, nutze ich BEM-Konventionen:
/* Statt */
.info-box { }
.info-box p { }
.info-box.warning { }
/* BEM */
.info-box { }
.info-box__content { }
.info-box--warning { }
Langfristig: Optional Sass/SCSS
Wenn ich merke, dass ich viele Mixins oder komplexe Verschachtelungen brauche, ist Sass der logische nächste Schritt. Aber: Modernes CSS kann mittlerweile sehr viel - natives Nesting kommt!
Fazit
Es gibt keine "beste" Methode - nur die richtige für dein Projekt. Die wichtigsten Takeaways:
- Dateiaufteilung ist der einfachste erste Schritt
- BEM löst Namenskonflikte und Spezifitätsprobleme
- ITCSS gibt dir eine Architektur für große Projekte
- Sass/SCSS macht CSS mächtiger, braucht aber Build-Tools
- CSS-in-JS ist perfekt für komponentenbasierte Frameworks
- Tailwind eliminiert CSS fast komplett - wenn du das magst
- CSS Layers sind die native Zukunft der CSS-Organisation
Und das Wichtigste: Jeder kämpft mit CSS-Organisation. Du bist in guter Gesellschaft!
Du musst nicht alles auf einmal ändern! Refactoring im laufenden Betrieb - neue Komponenten nach neuen Regeln, alte nach und nach migrieren.
Mehr aus CSS
Tutorials werden geladen...