Flexbox: quanto è grande quella scatola flessibile?

Pubblicato: 2022-03-10
Riassunto veloce ↬ Negli ultimi due articoli, abbiamo esaminato cosa succede quando creiamo un contenitore flessibile e abbiamo anche dato un'occhiata all'allineamento. Questa volta esploriamo il problema spesso confuso del dimensionamento in Flexbox. In che modo Flexbox decide quanto dovrebbero essere grandi le cose?

Questa è la terza parte della mia serie su Flexbox. Negli ultimi due articoli, abbiamo esaminato cosa succede quando crei un contenitore flessibile e abbiamo esplorato l'allineamento mentre funziona in Flexbox. Questa volta diamo un'occhiata alle taglie. Come controlliamo le dimensioni dei nostri articoli flessibili e quali scelte fa il browser quando controlla le dimensioni?

Visualizzazione iniziale di articoli flessibili

Se ho un set di elementi, che hanno lunghezze di contenuto variabili all'interno, e imposto il loro genitore per display: flex , gli elementi verranno visualizzati come una riga e si allineeranno all'inizio di quell'asse. Nell'esempio seguente i miei tre elementi hanno una piccola quantità di contenuto e sono in grado di visualizzare il contenuto di ogni elemento come una riga ininterrotta. C'è spazio all'estremità del contenitore flessibile in cui gli elementi non crescono perché il valore iniziale di flex-grow è 0 , non crescere .

Tre elementi con spazio alla fine
Gli elementi flessibili hanno spazio per essere visualizzati ciascuno su una riga (anteprima grande)

Se aggiungo più testo a questi elementi, alla fine riempiono il contenitore e il testo inizia a scorrere. Alle caselle viene assegnata una porzione dello spazio nel contenitore che corrisponde alla quantità di testo contenuta in ciascuna casella: a un elemento con una stringa di testo più lunga viene assegnato più spazio. Ciò significa che non ci ritroviamo con una colonna alta e magra con molto testo quando l'elemento della porta accanto contiene solo una singola parola.

Tre elementi, l'elemento finale ha un testo più lungo e il testo va a capo
Lo spazio è distribuito per dare più spazio a un elemento più lungo (Anteprima grande)

È probabile che questo comportamento ti sia familiare se hai mai utilizzato Flexbox, ma forse ti sei chiesto come sta funzionando il browser con quel ridimensionamento, come se guardi in più browser moderni vedrai che fanno tutti la stessa cosa. Ciò è dovuto al fatto che dettagli come questo sono elaborati nelle specifiche, assicurandosi che chiunque implementi Flexbox in un nuovo browser o altro agente utente sia a conoscenza di come dovrebbe funzionare questo calcolo. Possiamo usare le specifiche per trovare queste informazioni da soli.

Altro dopo il salto! Continua a leggere sotto ↓

La specifica di dimensionamento intrinseca ed estrinseca CSS

Scoprirai abbastanza rapidamente quando guardi qualcosa sul dimensionamento nelle specifiche Flexbox, che molte delle informazioni di cui hai bisogno si trovano in un'altra specifica: CSS Intrisnic ed Extrinsic Sizing. Questo perché i concetti di dimensionamento che stiamo utilizzando non sono esclusivi di Flexbox, allo stesso modo in cui le proprietà di allineamento non sono esclusive di Flexbox. Tuttavia, per come questi costrutti di dimensionamento vengono utilizzati in Flexbox, è necessario guardare nelle specifiche di Flexbox. Può sembrare un po' come se stessi saltando avanti e indietro, quindi radunerò alcune definizioni chiave qui, che userò nel resto dell'articolo.

Dimensione preferita

La dimensione preferita di una scatola è la dimensione definita da una width o height , o gli alias logici per queste proprietà di inline-size e block-size . Usando:

 .box { width: 500px; }

O l'alias logico inline-size :

 .box { inline-size: 500px; }

Stai affermando che vuoi che la tua casella sia larga 500 pixel o 500 pixel nella direzione in linea.

Dimensione del contenuto minimo

La dimensione del contenuto minimo è la dimensione più piccola che può essere una scatola senza causare un overflow. Se la tua casella contiene testo, verranno sfruttate tutte le possibili opportunità di soft-wrapping.

Dimensione massima del contenuto

La dimensione massima del contenuto è la dimensione più grande che la scatola può avere per contenere il contenuto. Se la casella contiene testo senza formattazione per suddividerlo, verrà visualizzata come una lunga stringa ininterrotta.

Dimensione principale articolo flessibile

La dimensione principale di un articolo flessibile è la dimensione che ha nella dimensione principale. Se stai lavorando in fila, in inglese, la dimensione principale è la larghezza. In una colonna in inglese, la dimensione principale è l'altezza.

Gli articoli hanno anche una dimensione principale minima e massima definita dalla loro min-width min-height sulla dimensione principale.

Elaborazione delle dimensioni di un articolo flessibile

Ora che abbiamo definito alcuni termini, possiamo dare un'occhiata a come sono dimensionati i nostri articoli flessibili. I valori iniziali delle proprietà flex sono i seguenti:

  • flex-grow: 0
  • flex-shrink: 1
  • flex-basis: auto

La flex-basis è la cosa da cui viene calcolato il dimensionamento. Se impostiamo flex-basis su 0 e flex-grow su 1, tutte le nostre scatole non hanno larghezza iniziale, quindi lo spazio nel contenitore flessibile viene distribuito in modo uniforme, assegnando la stessa quantità di spazio a ciascun elemento.

Guarda Pen Smashing Flexbox Series 3: flex: 1 1 0; di Rachel Andrew (@rachelandrew) su CodePen.

Guarda Pen Smashing Flexbox Series 3: flex: 1 1 0; di Rachel Andrew (@rachelandrew) su CodePen.

Se invece flex-basis è auto e flex-grow: 1 , viene distribuito solo lo spazio libero, tenendo conto delle dimensioni del contenuto.

Vedi Pen Smashing Flexbox Series 3: flex: 1 1 testo breve automatico di Rachel Andrew (@rachelandrew) su CodePen.

Vedi Pen Smashing Flexbox Series 3: flex: 1 1 testo breve automatico di Rachel Andrew (@rachelandrew) su CodePen.

In situazioni in cui non c'è spazio libero, ad esempio quando abbiamo più contenuti di quanti possono stare in una singola riga, allora non c'è spazio da distribuire.

Vedi Pen Smashing Flexbox Series 3: flex: 1 1 auto long text di Rachel Andrew (@rachelandrew) su CodePen.

Vedi Pen Smashing Flexbox Series 3: flex: 1 1 auto long text di Rachel Andrew (@rachelandrew) su CodePen.

Questo ci mostra che capire cosa significa auto è piuttosto importante se vogliamo sapere come Flexbox calcola le dimensioni delle nostre scatole. Il valore auto sarà il nostro punto di partenza.

Definizione automatica

Quando auto è definito come un valore per qualcosa in CSS, avrà un significato molto specifico in quel contesto, a cui vale la pena dare un'occhiata. Il CSS Working Group dedica molto tempo a capire cosa significhi auto in qualsiasi contesto, come spiega questo discorso per l'editore delle specifiche Fantasai.

Possiamo trovare le informazioni su cosa significa auto quando viene utilizzato come flex-basis nelle specifiche. I termini sopra definiti dovrebbero aiutarci a sviscerare questa affermazione.

“Quando specificata su un elemento flessibile, la parola chiave auto recupera il valore della proprietà dimensione principale come `base flessibile` utilizzata. Se quel valore è esso stesso automatico, il valore utilizzato è `content`."

Quindi, se la nostra flex-basis è auto , Flexbox esamina la proprietà della dimensione principale definita. Avremmo una dimensione principale se avessimo dato una width a uno qualsiasi dei nostri articoli flessibili. Nell'esempio seguente, gli elementi hanno tutti una larghezza di 110px, quindi questa viene utilizzata come dimensione principale poiché il valore iniziale per flex-basis è auto.

Guarda Pen Smashing Flexbox Series 3: articoli flessibili con una larghezza di Rachel Andrew (@rachelandrew) su CodePen.

Guarda Pen Smashing Flexbox Series 3: articoli flessibili con una larghezza di Rachel Andrew (@rachelandrew) su CodePen.

Tuttavia, il nostro esempio iniziale ha elementi che non hanno larghezza, ciò significa che la loro dimensione principale è auto e quindi dobbiamo passare alla frase successiva, "Se quel valore è esso stesso auto, il valore utilizzato è content ".

Ora dobbiamo guardare cosa dice la specifica sulla parola chiave content . Questo è un altro valore che puoi utilizzare (nei browser di supporto) per la tua flex-basis , ad esempio:

 .item { flex: 1 1 content; }

La specifica definisce il content come segue:

“Indica una dimensione automatica in base al contenuto dell'articolo flessibile. (In genere è equivalente alla dimensione massima del contenuto, ma con modifiche per gestire le proporzioni, i vincoli di dimensionamento intrinseci e i flussi ortogonali"

Nel nostro esempio, con elementi flessibili che contengono testo, possiamo ignorare alcune delle regolazioni più complicate e considerare il content come la dimensione massima del contenuto.

Quindi questo spiega perché, quando abbiamo una piccola quantità di testo in ogni elemento, il testo non va a capo. Gli articoli flessibili vengono ridimensionati automaticamente, quindi Flexbox controlla la dimensione massima del contenuto, gli articoli si adattano al loro contenitore a quella dimensione e il lavoro è fatto!

La storia non finisce qui, poiché quando aggiungiamo più contenuti le scatole non rimangono alla dimensione massima del contenuto. Se lo facessero, romperebbero il contenitore flessibile e causerebbero un trabocco. Una volta riempito il contenitore, il contenuto inizia ad avvolgersi e gli articoli assumono dimensioni diverse in base al contenuto al loro interno.

Risoluzione di lunghezze flessibili

È a questo punto che la specifica diventa ragionevolmente complessa, tuttavia, i passaggi che devono essere eseguiti sono i seguenti:

Innanzitutto, somma la dimensione principale di tutti gli articoli e verifica se è più grande o più piccola dello spazio disponibile nel contenitore.

Se la dimensione del contenitore è maggiore del totale, ci preoccuperemo del fattore flex-grow , poiché abbiamo spazio per crescere.

elementi flessibili con spazio libero alla fine
Nel primo caso i nostri articoli hanno spazio disponibile in cui crescere. (Grande anteprima)

Se la dimensione del contenitore è inferiore al totale, ci preoccuperemo del fattore flex-shrink poiché dobbiamo ridurlo.

flettere gli oggetti che traboccano dal contenitore
Nel secondo caso i nostri articoli sono troppo grandi e devono rimpicciolirsi per entrare nel contenitore. (Grande anteprima)

Blocca tutti gli articoli non flessibili, il che significa che possiamo già decidere una taglia per determinati articoli. Se stiamo usando flex-grow questo includerebbe tutti gli elementi che hanno flex-grow: 0 . Questo è lo scenario che abbiamo quando i nostri articoli flessibili hanno spazio lasciato nel contenitore. Il valore iniziale di flex-grow è 0, quindi diventano grandi quanto la loro larghezza massima e quindi non crescono più dalla loro dimensione principale.

Se utilizziamo flex-shrink , questo includerebbe tutti gli articoli con flex-shrink: 0 . Possiamo vedere cosa succede in questo passaggio se diamo al nostro set di elementi flex-shrink di 0. Gli elementi si congelano nel loro stato max-content e quindi non si flettono e si dispongono per adattarsi al contenitore.

Guarda Pen Smashing Flexbox Series 3: flex: 0 0 auto di Rachel Andrew (@rachelandrew) su CodePen.

Guarda Pen Smashing Flexbox Series 3: flex: 0 0 auto di Rachel Andrew (@rachelandrew) su CodePen.

Nel nostro caso, con i valori iniziali degli articoli flessibili, i nostri articoli possono ridursi. Quindi i passaggi continuano e l'algoritmo entra in un ciclo in cui calcola quanto spazio assegnare o togliere. Nel nostro caso stiamo usando flex-shrink perché la dimensione totale dei nostri articoli è maggiore del contenitore, quindi dobbiamo togliere spazio.

Il fattore flex-shrink viene moltiplicato per la dimensione della base interna degli articoli, nel nostro caso è la dimensione max-content . Questo dà un valore con cui ridurre lo spazio. Se gli oggetti rimuovevano spazio solo in base al fattore flex-shrink gli oggetti piccoli potrebbero sostanzialmente svanire, avendo rimosso tutto il loro spazio, mentre l'elemento più grande ha ancora spazio per restringersi.

C'è un passaggio aggiuntivo in questo ciclo per verificare la presenza di articoli che diventerebbero più piccoli o più grandi della loro dimensione principale target, nel qual caso l'articolo smette di crescere o restringersi. Ancora una volta, questo serve per evitare che alcuni oggetti diventino piccoli o enormi rispetto al resto degli oggetti.

Tutto ciò è stato semplificato in termini di specifiche poiché non ho esaminato alcuni degli scenari più spigolosi e in genere puoi semplicemente approfondire la tua mente, supponendo che tu sia felice di lasciare che Flexbox faccia le sue cose e non cerchi pixel perfezione. Ricordare i seguenti due fatti funzionerà nella maggior parte dei casi.

Se stai crescendo da auto , la flex-basis verrà considerata come qualsiasi larghezza o altezza sull'elemento o come dimensione max-content . Lo spazio verrà quindi assegnato in base al fattore flex-grow utilizzando quella dimensione come punto di partenza.

Se stai riducendo da auto , la flex-basis verrà considerata come qualsiasi larghezza o altezza sull'elemento o come dimensione max-content . Lo spazio verrà quindi rimosso in base alla dimensione della flex-basis moltiplicata per il fattore flex-shrink , e quindi rimosso in proporzione alla dimensione massima del contenuto degli articoli.

Controllo della crescita e del restringimento

Ho passato la maggior parte di questo articolo a descrivere cosa fa Flexbox quando viene lasciato a se stesso. Ovviamente puoi esercitare un maggiore controllo sui tuoi articoli flessibili utilizzando le proprietà flex . Si spera che sembrino più prevedibili con una comprensione di ciò che sta accadendo dietro le quinte.

Impostando la tua flex-basis o assegnando all'articolo stesso una dimensione che viene quindi utilizzata come flex-basis riprendi il controllo dall'algoritmo, dicendo a Flexbox che desideri aumentare o ridurre questa dimensione particolare. Puoi disattivare completamente la crescita o la riduzione impostando flex-grow o flex-shrink su 0. Su questo punto, tuttavia, vale la pena usare il desiderio di controllare gli elementi flessibili come momento per verificare se stai utilizzando il metodo di layout corretto. Se ti ritrovi a provare ad allineare elementi flessibili in due dimensioni, potresti scegliere meglio il layout della griglia.

Problemi relativi alle dimensioni del debug

Se i tuoi articoli flessibili stanno raggiungendo una dimensione inaspettata, di solito è perché la tua base flessibile è automatica e c'è qualcosa che dà a quell'oggetto una larghezza, che viene quindi utilizzata come base flessibile. L'ispezione dell'elemento in DevTools può aiutare a identificare da dove proviene la dimensione. Puoi anche provare a impostare una flex-basis di 0 che costringerà Flexbox a trattare l'elemento come avente larghezza zero. Anche se questo non è il risultato che desideri, ti aiuterà a identificare il valore della flex-basis in uso come il colpevole dei tuoi problemi di dimensionamento.

Lacune flessibili

Una caratteristica molto richiesta di Flexbox è la possibilità di specificare spazi vuoti o grondaie tra elementi flessibili nello stesso modo in cui possiamo specificare gli spazi vuoti nel layout della griglia e nel layout a più colonne. Questa funzione è specificata per Flexbox come parte di Box Alignment e la prima implementazione del browser è in arrivo. Firefox prevede di fornire le proprietà del gap per Flexbox in Firefox 63. L'esempio seguente può essere visualizzato in Firefox Nightly.

Guarda Pen Smashing Flexbox Series 3: flex-gaps di Rachel Andrew (@rachelandrew) su CodePen.

Guarda Pen Smashing Flexbox Series 3: flex-gaps di Rachel Andrew (@rachelandrew) su CodePen.
Tre file di elementi con spaziatura tra le grondaie
L'immagine vista in Firefox 63 (anteprima grande)

Come per il layout della griglia, viene presa in considerazione la lunghezza dello spazio vuoto prima che lo spazio venga distribuito agli elementi flessibili.

Avvolgendo

In questo articolo, ho cercato di spiegare alcuni dei punti più fini di come Flexbox calcola quanto sono grandi gli articoli flessibili. Può sembrare un po' accademico, tuttavia, dedicare del tempo per capire come funziona può farti risparmiare enormi quantità di tempo quando usi Flexbox nei tuoi layout. Trovo davvero utile tornare al fatto che, per impostazione predefinita, Flexbox sta cercando di darti il ​​layout più sensato di un gruppo di articoli con dimensioni variabili. Se un elemento ha più contenuti, gli viene concesso più spazio. Se tu e il tuo design non siete d'accordo con ciò che Flexbox pensa sia il migliore, potete riprendere il controllo impostando la vostra flex-basis .