Flexbox – Responsive Layouts ohne Media Queries
Mit Flexbox können automatisch responsive Komponenten erzeugt werden, die eigene Breakpoints besitzen, jedoch keine Media Queries benötigen.
Innerhalb von Flexbox kann mit den Eigenschaften flex-grow
, -shrink
& -basis
festgelegt werden, ob Elemente größer werden dürfen, ob sie kleiner werden dürfen und welche Ausgangsgröße zugrunde liegt. Mit Flexbox lassen sich somit responsive Layouts herstellen, die keine Media Queries benötigen. Das wiederum gilt aktuell in einigen Anwendungsfällen als »Best Practise«, da in sich abgeschlossene Komponenten entwickelt werden können, die nicht auf die Größe des Viewports sondern auf den verfügbaren Platz im Elternelement reagieren.
Automatisch umbrechende Spalten
Stellen wir uns als Beispiel für diesen Beitrag eine »Card-Komponente« vor, die aus einem Bildbereich und aus einem Textbereich besteht. Wenn die Komponente viel Platz hat, soll das Bild neben dem Text angezeigt werden – bei wenig Platz ist das Bild über dem Text.
Mit folgendem Code kann das gewünschte Ergebnis erreicht werden, ohne dass dafür ein Media Query notwendig ist.
<div class="card">
<div class="media"></div>
<div class="content"></div>
</div>
.card {
display: flex;
flex-wrap: wrap;
background: silver;
}
.card > * {
flex-grow: 1;
flex-shrink: 1;
flex-basis: 280px;
}
.media {
background: black;
min-height: 280px;
}
Der äußere Container (.card
) ist eine Flexbox, was dazu führt, dass standardmäßig die beiden enthaltenen Kind-Elemente nebeneinander und gleich hoch angezeigt werden. Mit flex-wrap
wird festgelegt, dass die Kindelemente umbrechen dürfen, wenn zu wenig Platz zur Verfügung steht.
Die Kindelemente selbst dürfen dank flex-grow: 1;
größer und dank flex-shrink: 1;
kleiner werden und erhaltenen einen Ausgangswert für die Breite von 280 Pixeln. Dieser Wert ist der »Breakpoint« der Komponente. Sobald eine der beiden Spalten weniger als 280 Pixel zur Verfügung hat, brechen die Elemente um und verschieben sich untereinander. Da sie wachsen und schrumpfen dürfen, sind sie auch in dieser Anordnung von der Breite her flexibel.
Mehrere Elemente umbrechen lassen
Die Card-Komponente kann auch mehrfach nebeneinander verwendet werden. Das Prinzip aus dem obigen Beispiel wird dann noch einmal auf höherer Ebene wiederholt.
Wenn Sie drei Mal zum Einsatz kommt, lässt sich ein interessanter Effekt erkennen: Die dritte Card rutsch im Zwischenschritt quer unter die anderen beiden und nimmt – da viel Platz zur Verfügung steht – automatisch die Darstellung mit Bild links und Text rechts ein.
Der Code unterscheidet sich nur geringfügig vom vorherigen Beispiel. Es wurde lediglich ein Container hinzugefügt und als Flexbox definiert. Zusätzlich wird den Kind-Elemtenten (.card
) eine flex-basis
zugewiesen.
.container {
display: flex;
flex-wrap: wrap;
}
.container > * {
flex: 1 1 calc(280px + 1em)); /* 1em margin als Spaltenabstand berücksichtigt, calc() nicht notwendig */
}
Umbruch ohne Zwischenschritt
Der Zwischenschritt kann nun natürlich als sehr unschön empfunden werden – je nach gestalterischer Ausprägung des Projekts. Um den Zwischenschritt zu überspringen gibt es einen Trick, der erstmals im Artikel The Flexbox Holy Albatross beschrieben wurde. Die Anpassung führt dazu, dass die drei Card-Elemente entweder nebeneinander oder untereinander angezeigt werden. Nach wie vor reagieren sie auf unterschiedlich viel Platz und strukturieren sich selbstständig um.
Der Trick arbeitet mit einer Berechnung des flex-basis
-Werts, die dazu führt, dass bei wenig Platz extrem kleine und bei viel Platz extrem große Werte entstehen. Somit wird die Komponente in ihre beiden Extremzustände gezwungen und der Zwischenschritt verschwindet. Eine detaillierte Erklärung des Tricks findet ihr hier.
.card {
display: flex;
flex-wrap: wrap;
flex-basis: calc(960px * 999 - 100% * 999);
}
Nach einigem Herumprobieren, habe ich eine Lösung für mein Problem gefunden. War aber nicht unbedingt intuitiv:
https://jsfiddle.net/3svdbj67/
Gruß
Marc
Hey Jonas,
ich habe in meinem Design für große Bildschirme mehrere Karten untereinander, bei denen Bild und Text abwechselnd mal links und mal rechts sind. Im Design für kleine Bildschirme kommt IMMER erst das Bild, dann der Text. Mit klassischen Breakpoints kein Problem, dank „order“.
Hättest du eine Idee, wie ich das nur mit Flexbox lösen könnte? Also wie kann man die Reihenfolge der „flex items“ ohne Media Queries ändern?
Gruß
Marc
Danke für die tolle flexbox-Seite. Was mir fehlt ist folgendes: Ich möchte 3 Spalten haben und darunter wieder 3. Gibts dazu einen break, der nach einer gewissen Anzahl an Spalten wieder neu beginnt?
Hallo Herbert, du kannst
flex-wrap: wrap
auf dem Flex-Container verwenden und dann den Flex-Items 33.333% Breite bzw.flex-basis
zuweisen. Dann sollte es passen. Details zu Flexbox-Grundlagen findest du auch hier.Also so richtig gut gewählt sind die Beispiele aber nicht. Richtige Bilder skalieren ja auch nicht ohne Ende und wenn dann sehen sie völlig unbrauchbar aus wenn die mehr als doppelt so groß sind. Je nach TExtmenge ist es auch immer unterschiedlich. Unter realen Bedingungen ist da noch einiges an Anpassung nötig.
Hallo Alex, klar – es sind Beispiele für diese Technik, aber welches Problem siehst du denn da? Die Bilder würden wahrscheinlich mit
srcset
undsizes
ausgetauscht werden. Sie passen sich also der Qualität an. Und die Textmenge ist auch recht flexibel änderbar.Vielen Dank für hilfreichen Beitrag! Ich werde natürlich Ihren Blog meinen Kollegen weiterempfehlen.
Mit CSS Grid benötigt man sogar nur 1 Codezeile:
.container {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(280px, 1fr);
}
Korrekt. Haben wir hier ausführlich beschrieben.
Hallo Jonas,
ich bin durch Zufall auf deinen Blog gestoßen, als ich Infos für responsives Webdesign suchte. Was mich interessiert, ist, wie kompatibel sind die Browser bei der Verwendung von flexbox Layouts?
MfG maclinux
Der Browser-Support ist sehr gut. Flexbox kann problemlos eingesetzt werden. Details findest du bei caniuse.com