Icons und Illustrationen im Dark Mode mit Tailwind sauber anpassen
AI generated
tw
Tailwind CSS · Dark Mode · SVG · Illustration
Icons und Illustrationen
im Dark Mode mit Tailwind sauber anpassen statt nur zu invertieren

Ein Dark Mode für Text und Flächen lässt sich mit Tailwinds dark:-Variante meist zügig umsetzen, aber Icons und vor allem komplexe Illustrationen stellen ein eigenes Problem dar. Eine simple CSS-Filter-Invertierung macht aus einer mehrfarbigen Illustration schnell ein unleserliches Farbchaos, weil Invertierung jede Farbe unabhängig von ihrer ursprünglichen Bedeutung umkehrt. Wer stattdessen gezielt mit dark:-Varianten auf SVG-Ebene arbeitet, behält die volle Kontrolle über Fill, Stroke und Kontrast in beiden Modi.

14 Min. Lesezeit SVG · fill/stroke · dark: WCAG 1.4.11 Non-Text-Kontrast

1. Warum reine Farbinvertierung bei komplexen Illustrationen scheitert

Der schnellste vermeintliche Weg zu einer Dark-Mode-tauglichen Illustration ist ein CSS-Filter wie filter: invert(1), angewendet auf das gesamte SVG oder Bild. Bei einem simplen Ein-Farb-Icon mag das noch funktionieren, weil Schwarz zu Weiß wird und umgekehrt. Sobald eine Illustration aber mehrere Farben enthält, etwa ein blaues Element, ein oranges Akzentdetail und einen beigen Hintergrund, kehrt die Invertierung jede dieser Farben unabhängig um und erzeugt Kombinationen, die mit der ursprünglichen Bildaussage nichts mehr zu tun haben.

Besonders deutlich wird das Problem bei Illustrationen mit Hauttönen, Markenfarben oder feinen Farbverläufen: Ein invertiertes Beige wirkt plötzlich blaugrau, eine invertierte Markenfarbe trifft nicht mehr den Farbton aus dem Styleguide, und Farbverläufe können unnatürliche Kanten bekommen. Ein hue-rotate zusätzlich zur Invertierung repariert oft nur einen Teil des Problems und führt bei anderen Farben im selben Bild zu neuen Verzerrungen, weil ein einziger globaler Filter niemals jede Farbe im Bild einzeln korrekt behandeln kann.

2. Die dark:-Variante gezielt für SVG-Fill und -Stroke einsetzen

Für einfache Icons, die als Inline-SVG im Markup liegen, ist Tailwinds dark:-Variante der direkteste Weg. Statt das komplette Bild zu filtern, steuert man die Farbe einzelner Pfade gezielt über die fill- und stroke-Attribute, indem das SVG fill="currentColor" nutzt und die Textfarbe der umschließenden Klasse mit einer dark:-Variante versehen wird. So erbt das Icon im Light Mode eine dunkle und im Dark Mode automatisch eine helle Farbe, ganz ohne eigenen Filter.

Bei mehrfarbigen Icons, bei denen nicht alle Pfade dieselbe Farbe teilen sollen, lassen sich einzelne path- oder g-Elemente direkt mit Tailwind-Klassen versehen, etwa class="fill-blue-600 dark:fill-blue-400" auf einem bestimmten Pfad und class="fill-gray-800 dark:fill-gray-200" auf einem anderen. Diese granulare Kontrolle ist zwar aufwendiger als ein globaler Filter, liefert aber ein Ergebnis, das in beiden Modi tatsächlich wie dieselbe Illustration aussieht, nur eben in angepassten Tonwerten.


<!-- Inline-SVG mit currentColor: erbt Textfarbe inklusive dark: -->
<span class="text-gray-700 dark:text-gray-300">
  <svg viewBox="0 0 24 24" fill="currentColor" class="h-6 w-6">
    <path d="M12 2 2 7l10 5 10-5-10-5Z" />
  </svg>
</span>

<!-- Mehrfarbiges Icon mit gezielten fill-Klassen je Pfad -->
<svg viewBox="0 0 48 48" class="h-10 w-10">
  <path d="M4 24a20 20 0 1 1 40 0" class="fill-sky-600 dark:fill-sky-400" />
  <circle cx="24" cy="24" r="6" class="fill-amber-500 dark:fill-amber-300" />
</svg>

3. Zwei getrennte Illustrationssets versus dynamische CSS-Variablen

Bei aufwendigen Illustrationen mit vielen Farbflächen, Verläufen und feinen Details stößt die pfadweise dark:-Klassenvergabe schnell an praktische Grenzen, weil ein einzelnes SVG dutzende Pfade enthalten kann. Hier bieten sich zwei grundsätzliche Strategien an: entweder pflegt man zwei komplett getrennte Illustrationsdateien, eine für Light Mode und eine eigens für Dark Mode gestaltete Variante, oder man baut die Illustration einmal mit CSS-Custom-Properties für jede Farbfläche und überschreibt diese Variablen im Dark Mode zentral.

Zwei getrennte Sets liefern das visuell beste Ergebnis, weil ein Designer im Dark-Mode-Set gezielt Kontraste, Verläufe und sogar Kompositionsdetails anpassen kann, die im Light Mode anders wirken würden. Der Nachteil ist der doppelte Pflegeaufwand bei jeder Aenderung. Die CSS-Variablen-Lösung ist wartungsfreundlicher, weil nur ein SVG existiert, schränkt aber die gestalterische Freiheit ein, da sich per Definition nur Farbwerte austauschen lassen, nicht aber Formen oder Kompositionen.

4. Illustrationen mit CSS-Custom-Properties dynamisch einfärben

Für die Variablen-Lösung bekommt jede relevante Farbfläche im SVG eine eigene CSS-Custom-Property als Füllfarbe, etwa fill: var(--illu-primary) und fill: var(--illu-accent). Diese Variablen werden im normalen Stylesheet mit den Light-Mode-Werten definiert und anschließend innerhalb der dark:-Media-Query oder der entsprechenden Tailwind-Dark-Klasse auf dem umschließenden Container mit anderen Werten überschrieben. Das SVG selbst bleibt dabei vollkommen unverändert, nur der Kontext, in dem es gerendert wird, entscheidet über die Farben.

Dieser Ansatz lässt sich gut mit Tailwind v4 kombinieren, indem die Variablen im @theme-Block oder direkt in einer Utility-Klasse mit @layer components definiert werden. Der praktische Vorteil zeigt sich vor allem bei Illustrationen, die mehrfach auf einer Seite auftauchen, etwa in einer Feature-Liste mit vier gleichartigen Icons: Eine zentrale Variablenänderung wirkt sich sofort auf alle Vorkommen aus, während bei getrennten SVG-Dateien jede Instanz einzeln ausgetauscht werden müsste.

5. Kontrastprüfung für Icons speziell im Dark Mode

Für reinen Text gilt WCAG-Kriterium 1.4.3 mit einem Mindestkontrast von 4,5 zu 1, aber für grafische Objekte wie Icons und deren Umrandungen ist stattdessen Kriterium 1.4.11, der sogenannte Non-Text-Kontrast, maßgeblich. Es verlangt ein Kontrastverhältnis von mindestens 3 zu 1 zwischen dem Icon und seiner unmittelbaren Umgebung, sofern das Icon zum Verständnis der Oberfläche notwendig ist, etwa ein Warnsymbol oder ein Statusindikator. Ein zu blasses Grau, das im Light Mode noch ausreichend Kontrast bot, fällt im Dark Mode auf dunklem Hintergrund oft unter diesen Schwellenwert.

In der Praxis lohnt es sich, jede im Projekt verwendete Icon-Grundfarbe für beide Modi einzeln mit einem Kontrastrechner gegen den jeweils typischen Hintergrund zu prüfen, statt sich auf ein Gefühl für ausreichende Sichtbarkeit zu verlassen. Besonders tückisch sind dabei mittelgraue Töne, die in beiden Modi auf den ersten Blick akzeptabel wirken, bei genauer Messung aber in einem der beiden Modi unter die 3-zu-1-Schwelle rutschen und dann gezielt für den jeweiligen Modus angepasst werden müssen.

6. Fallback-Strategie für Icon-Bibliotheken ohne eingebaute Dark-Mode-Unterstützung

Viele fertige Icon-Sets, die als einfarbige SVG-Dateien ausgeliefert werden, unterstützen das currentColor-Muster von Haus aus, weil sie ohnehin nur eine Linienfarbe verwenden. Bei solchen Sets reicht in der Regel schon eine text-*- beziehungsweise dark:text-*-Klasse auf dem umschließenden Element, ohne dass an der SVG-Datei selbst etwas verändert werden muss. Problematisch wird es nur bei Icon-Sets, die feste Hex-Farben direkt im fill-Attribut jedes einzelnen Pfades hart codiert mitliefern.

In diesem Fall lohnt sich ein einmaliger Bereinigungsschritt beim Import: Alle harten fill="#000000"-Attribute werden per Suchen-und-Ersetzen oder einem kleinen Build-Skript durch fill="currentColor" ersetzt, bevor die Datei ins Projekt übernommen wird. Dieser einmalige Aufwand zahlt sich aus, weil danach jedes Icon aus dem Set automatisch von der zentralen dark:-Farbsteuerung profitiert, statt bei jedem neuen Icon erneut manuell nachgebessert werden zu müssen.

7. Performance-Ueberlegungen bei zwei parallelen Illustrationssets

Wer sich für zwei getrennte Illustrationssets entscheidet, sollte vermeiden, im Markup beide Varianten gleichzeitig zu laden und nur per CSS ein- oder auszublenden, weil dann tatsächlich doppelt so viele Bilddaten übertragen werden, selbst wenn nur eine Variante sichtbar ist. Sinnvoller ist es, serverseitig oder per JavaScript anhand der bereits bekannten Farbschema-Präferenz nur das jeweils passende SVG in den DOM einzufügen, etwa über ein Alpine.js-x-show in Kombination mit x-cloak, damit kein kurzes Aufblitzen der falschen Variante entsteht.

Bei Inline-SVGs, die direkt im HTML eingebettet sind, fällt dieses Problem geringer aus, weil kein zusätzlicher Netzwerk-Request nötig ist, aber die reine DOM-Größe wächst trotzdem, wenn beide Sets parallel im Markup liegen. Für Illustrationen, die nicht above the fold liegen, ist ein einfacher, serverseitig anhand eines Cookies oder prefers-color-scheme vorentschiedener Ansatz meist die pragmatischste Lösung, weil er unnötigen Overhead im initialen Rendering vermeidet.

8. Häufige Fehler bei Icons und Illustrationen im Dark Mode

Ein häufiger Fehler ist, Icons pauschal mit derselben Graustufe wie den Fließtext einzufärben, ohne zu bedenken, dass Icons als grafische Objekte einer anderen Kontrastregel unterliegen als Text. Ein zweiter verbreiteter Fehler ist der Einsatz von filter: invert() auf komplette Illustrationen, was, wie eingangs beschrieben, bei mehrfarbigen Bildern fast immer zu unerwünschten Farbverschiebungen führt und im Ergebnis oft schlechter aussieht als gar keine Dark-Mode-Anpassung.

Ein dritter Fehler betrifft transparente PNG- oder WebP-Illustrationen mit dunklen Konturlinien, die im Light Mode auf hellem Grund gut funktionieren, im Dark Mode aber plötzlich fast unsichtbar werden, weil dunkle Linien auf dunklem Hintergrund kaum noch Kontrast bieten. Solche Rasterbilder lassen sich anders als SVGs nicht per CSS nachfärben, weshalb sie für konsequente Dark-Mode-Unterstützung fast immer durch SVG-Versionen ersetzt werden sollten, sobald das Projekt einen echten Dark Mode bekommt.

9. Fazit: Die passende Strategie je nach Icon-Komplexität wählen

Für einfache, einfarbige Icons ist currentColor in Kombination mit Tailwinds dark:text-*-Klassen fast immer der richtige und günstigste Weg, weil er ohne zusätzliche Dateien oder Variablen auskommt. Für mehrfarbige Icons mit wenigen Farbflächen lohnt sich die gezielte pfadweise fill-Klassenvergabe direkt im SVG, während für komplexe Illustrationen entweder zwei gepflegte Sets oder eine CSS-Variablen-Lösung je nach Team-Ressourcen und gewünschter gestalterischer Freiheit die bessere Wahl ist.

In jedem Fall gilt: Die Kontrastprüfung nach WCAG 1.4.11 sollte für beide Modi getrennt erfolgen, weil ein im Light Mode ausreichender Kontrast im Dark Mode keineswegs automatisch bestehen bleibt. Wer diese Prüfung als festen Schritt in den Review-Prozess neuer Icons und Illustrationen aufnimmt, vermeidet die häufigsten Dark-Mode-Regressionsprobleme, bevor sie überhaupt live gehen.

Strategie Aufwand Gestaltungsfreiheit Geeignet für
currentColor + dark:text-* Sehr niedrig Gering, nur eine Farbe Einfarbige Icons
Pfadweise fill-Klassen Mittel Mittel, mehrere Farbflächen Mehrfarbige Icons mit wenigen Pfaden
CSS-Custom-Properties Mittel bis hoch Nur Farbwerte austauschbar Wiederkehrende komplexe Illustrationen
Zwei getrennte SVG-Sets Hoch, doppelte Pflege Maximal, auch Form/Komposition Hero-Illustrationen, Marketing-Seiten

Mironsoft

Tailwind-CSS-Architektur, Design-Systeme und Performance

Tailwind-Frontends, die trotz tausender Utility-Klassen wartbar bleiben?

Wir prüfen bestehende Tailwind-Projekte auf aufgeblähte Klassenlisten, inkonsistente Design-Tokens und ungenutzte CSS-Reste und bauen daraus ein Design-System, das sich sauber skaliert statt mit jeder Komponente unübersichtlicher zu werden.

Design-System-Review

Tokens, Spacing-Skala und Komponentenkonsistenz auf Wartbarkeit prüfen.

Performance-Optimierung

CSS-Bundle-Größe, Purge-Konfiguration und Ladezeiten systematisch reduzieren.

Component-Architektur

Wiederverwendbare, gut strukturierte Komponenten statt Klassenlisten-Wildwuchs aufbauen.

10. Zusammenfassung

Icons und Illustrationen im Dark Mode: Das Wichtigste auf einen Blick

Problem mit Invertierung

filter: invert() kehrt jede Farbe unabhängig um und zerstört bei mehrfarbigen Illustrationen die ursprüngliche Bildaussage.

Einfache Icons

currentColor im SVG kombiniert mit Tailwinds dark:text-*-Klassen löst die meisten einfarbigen Icon-Fälle ohne Zusatzaufwand.

Komplexe Illustrationen

Entweder zwei gepflegte SVG-Sets für maximale Gestaltungsfreiheit oder CSS-Custom-Properties für wartungsarme Wiederverwendung.

Kontrastregel

WCAG 1.4.11 verlangt 3 zu 1 für bedeutungstragende Icons, getrennt für Light und Dark Mode zu prüfen.

11. FAQ: Icons und Illustrationen im Dark Mode: Das Wichtigste auf einen Blick

1Warum sieht filter: invert() bei Illustrationen im Dark Mode oft schlecht aus?
Weil die Invertierung jede Farbe im Bild unabhängig von ihrer ursprünglichen Bedeutung umkehrt. Bei mehrfarbigen Illustrationen entstehen dadurch Farbkombinationen, die mit dem originalen Design nichts mehr gemeinsam haben, etwa verfälschte Markenfarben oder unnatürlich wirkende Hauttöne.
2Wie färbt man ein einfarbiges SVG-Icon automatisch für Dark Mode ein?
Das SVG erhält fill="currentColor", und die umschließende Textfarbe wird mit einer Tailwind-Klasse wie text-gray-700 dark:text-gray-300 gesteuert. Das Icon erbt dann automatisch die jeweils aktive Textfarbe, ganz ohne eigenen CSS-Filter.
3Wie geht man bei mehrfarbigen Icons mit wenigen Pfaden vor?
Jeder relevante Pfad oder jede Gruppe im SVG bekommt eine eigene Tailwind-Klasse mit fill- und dark:fill-Wert, zum Beispiel fill-sky-600 dark:fill-sky-400 auf einem Pfad und fill-amber-500 dark:fill-amber-300 auf einem anderen.
4Wann lohnen sich zwei komplett getrennte Illustrationssets?
Bei aufwendigen Illustrationen mit vielen Farbflächen, Verläufen oder Kompositionsdetails, die im Dark Mode gezielt anders gestaltet werden sollen. Der Vorteil ist maximale gestalterische Freiheit, der Nachteil doppelter Pflegeaufwand bei jeder Aenderung.
5Wie funktioniert die CSS-Custom-Properties-Lösung für Illustrationen?
Jede Farbfläche im SVG referenziert eine CSS-Variable als fill-Wert, etwa fill: var(--illu-primary). Die Variable wird für Light Mode normal definiert und im Dark-Mode-Kontext mit einem anderen Wert überschrieben, während das SVG selbst unverändert bleibt.
6Welcher WCAG-Kontrastwert gilt für Icons statt für Text?
Kriterium 1.4.11, der Non-Text-Kontrast, verlangt mindestens 3 zu 1 zwischen einem bedeutungstragenden Icon und seiner unmittelbaren Umgebung, während Fließtext nach Kriterium 1.4.3 mindestens 4,5 zu 1 benötigt.
7Warum reicht ein im Light Mode ausreichender Icon-Kontrast im Dark Mode oft nicht?
Weil sich der Hintergrund grundlegend ändert und ein mittelgrauer Farbton, der auf Weiß ausreichend Kontrast bietet, auf einem dunklen Hintergrund oft unter die 3-zu-1-Schwelle fällt. Beide Modi müssen deshalb getrennt gemessen werden.
8Wie behandelt man fertige Icon-Bibliotheken mit hart codierten Hex-Farben?
Beim Import werden alle festen fill="#000000"-Attribute per Suchen-und-Ersetzen oder Build-Skript durch fill="currentColor" ersetzt. Danach profitiert jedes Icon automatisch von der zentralen dark:-Farbsteuerung über die umschließende Textfarbe.
9Was ist bei transparenten Raster-Illustrationen wie PNG im Dark Mode zu beachten?
Dunkle Konturlinien, die im Light Mode gut funktionieren, werden auf dunklem Hintergrund fast unsichtbar. Da sich Rasterbilder anders als SVGs nicht per CSS nachfärben lassen, sollten sie für echten Dark-Mode-Support durch SVG-Versionen ersetzt werden.
10Wie vermeidet man Performance-Probleme bei zwei parallelen Illustrationssets?
Statt beide Varianten zu laden und nur per CSS auszublenden, sollte serverseitig oder per JavaScript anhand der bekannten Farbschema-Präferenz nur das passende SVG in den DOM eingefügt werden, etwa mit Alpine.js x-show in Kombination mit x-cloak.