css flex inline
ich
- css
0
Rolf B
0 ich0
Rolf B
0
Gunnar Bittersmann
0
Rolf B
Hallo. Ihr werdet sicher sagen: das geht so nicht. Aber ich frage trotzdem :-)
Flex container werden mit style="display:flex; flex-wrap:wrap;" umgebrochen, wenn die Bildschirmbreite nicht ausreicht. Soll ja auch so.
Nun zur Frage: kann man es hinbekommen, dass die container nicht komplett umgebrochen werden, sondern nur tlw.? Nach dem Motto "Ein Bild sagt mehr als tausend Worte", hier ein Bild:
Geht das mit flex oder eher nicht?
Gruß, ich
PS: bevor Ihr nachfragt: ich verändere die Reihenfolge der container mit order in verschiedenen Situationen. Deshalb sind die einzelnen Texte in flex-containern.
Hallo ich,
ein Flexitem erzeugt einen eigenen Blockformatierungskontext und DESHALB geht das nicht.
Ausnahme: Das Flexitem ist selbst wieder ein Flex-Container. Dann erzeugt es einen Flexformatierungskontext. Aber der bricht auch nicht um.
Test:
<div class="flex">
<div>Das ist das erste Flexitem, nur für mich</div>
<div><span>Das ist das</span><span>zweite Flexitem,</span><span>nur für dich</span></div>
</div>
.flex {
display: inline-flex;
flex-flow: row wrap;
}
.flex div {
display: inline-flex;
flex-flow: row wrap;
gap: 0.25em;
}
bricht das zweite div trotzdem vollständig um.
Da die Anordnung mit order unzugänglich ist (ein Screenreader oder die Tab-Reihenfolge achten nicht auf order), würde ich Dir empfehlen, die Items im DOM mit JavaScript umzusortieren. Das ist etwas schwieriger, dürfte aber die wenigsten Probleme machen.
Ich zeige mal, wie man das macht.
<ol class="orderable itemlist">
<li value="2">Das ist das erste Flexitem, nur für mich. </li>
<li value="4">Das ist das zweite Flexitem, nur für dich. </li>
<li value="1">Das ist das dritte Flexitem, für ihn, sie und them. </li>
<li value="3">Das ist das vierte Flexitem, für die ganze Welt. </li>
<li value="1">Das ist das fünfte Flexitem, für Selfhtml. </li>
</ol>
Ich verwende eine Liste, weil es für li Elemente das value-Attribut gibt, das die Nummer des Items angibt. Man muss es für alle setzen, bzw. wo es nicht gesetzt ist, ist der Wert 0.
Man iteriert nun über alle Listen mit den Klassen orderable und itemlist (fühle Dich frei, die zu sortierenden Container anders zu identifizieren) und sortiert die Items der gefundenen Listen anhand des value-Attributs um.
Dieses Iterieren kann man so formulieren:
const orderables = document.querySelectorAll("ol.orderable.itemlist");
for (const orderable of orderables) {
...
}
oder kompakter so:
for (const orderable of document.querySelectorAll("ol.orderable.itemlist")) {
...
}
Felix würde jetzt sagen: dafür nimmt man die forEach-Methode. Ich nicht, das ist aus meiner Sicht veraltet, ich bevorzuge bei iterierbaren Sammlungen die for...of Schleife.
Im Inneren der Schleife muss man jetzt die Listitems einsammeln. Das geht geschickt mit einem :scope-Selektor und dem Kind-Kombinator für querySelectorAll:
const items = orderable.querySelectorAll(":scope > li")
Das Ergebnis ist eine Nodelist. Zum Sortieren braucht man aber ein Array. Die moderne Methode, aus einem iterierbaren Objekt ein Array zu machen, ist ein Arrayliteral mit spread-Operator:
const items = [ ...orderable.querySelectorAll(":scope > li") ];
Beachte: Es ist nicht nötig, die Zwischenergebnisse in Variablen zu speichern. Man kann direkt auf den Funktionsergebnissen weiterarbeiten.
DAS kann man nun mit der sort-Methode nach der order sortieren. Dafür braucht man sort mit Vergleichs-Callback. Da das value-Attribut immer numerisch ist, kann man a.value - b.value rechnen.
const items = [ ...orderable.querySelectorAll(":scope > li") ]
.sort( (a,b) => a.value > b.value );
Sort liefert das sortierte Array zurück, d.h. wir können dieses Ergebnis nun durchlaufen. Die items-Variable brauchen wir nicht mehr…
for (const orderable of document.querySelectorAll("ol.orderable.itemlist")) {
for (const sortedRef of
[...orderable.querySelectorAll(":scope > li")]
.sort( (a,b) => a.value - b.value )
) {
orderable.append(sortedRef)
}
}
Der append-Aufruf entfernt das Element von seiner aktuellen Position und hängt es hinten an die Liste der Kindelemente an. Bei gleicher value-Nummer sollten die Elemente so hintereinander stehen, wie sie vor dem Sortieren vorgefunden wurden.
Edit: Ich habe das überarbeitet, vorher waren es divs, jetzt ul/li, das ist viel einfacher und auch semantischer. Ich hoffe, ich habe nichts übersehen.
Rolf
Wow das ist ja mal ne Antwort. Danke! Ich werde es ausprobieren, auch wenn ich damit wohl mit Kanonen auf Spatzen schießen werde.
Danke nochmal und bald frohe Weihnacht
Hallo ich,
ich habe das nochmal überarbeitet. Die divs sind ungeschickt, ol/li ist besser.
Der Aufwand erscheint mir nicht übertrieben. Es ist ein winziges Script, und ob Du nun style-Attribute mit order-Eigenschaft oder value-Attribute setzt, macht keinen Unterschied.
Viel Erfolg!
Rolf
@@Rolf B
ich habe das nochmal überarbeitet. Die divs sind ungeschickt, ol/li ist besser.
Nein, das kann man in Unkenntnis der Inhalte, die ich da reinpackt[1], nicht sagen. Womöglich sind gar spans angebracht.
🖖 Live long and prosper
Die 3. Person ist hier völlig richtig, es geht um ich, nicht um mich. ↩︎
@@Rolf B
Da die Anordnung mit
orderunzugänglich ist (ein Screenreader oder die Tab-Reihenfolge achten nicht auf order)
In Chromium-Browsern ginge das schon – ist aber noch experimentell.
würde ich Dir empfehlen, die Items im DOM mit JavaScript umzusortieren.
Warum nicht serverseitig (mit PHP)?
🖖 Live long and prosper
Hallo Gunnar Bittersmann,
Warum nicht serverseitig (mit PHP)?
Wenn man das serverseitig bei der Seitengenerierung schon weiß, braucht man keine Spielchen mit order. Denk ich.
Rolf