Το flexbox είναι μια ιδιαίτερα χρήσιμη λειτουργία στη CSS που χρησιμοποιείται για την αναπαράσταση στοιχείων της HTML ως ευλύγιστα κουτιά, όπως υποδηλώνει ο όρος. Πιο συγκεκριμένα, είναι ένας βολικός τρόπος για να τοποθετούμε στον χώρο HTML στοιχεία και να αλλάζουμε τις διαστάσεις τους. Υπάρχει πληθώρα ιδιοτήτων που μπορούμε να εφαρμόσουμε πάνω σε στοιχεία μέσω του flexbox, εξού και ο λόγος που είναι τόσο δημοφιλές.
Τα βασικά του flexbox
Ας μιλήσουμε, αρχικά, για τα βασικά του flexbox. Όταν χρησιμοποιούμε το flexbox έχουμε ένα flex container, το οποίο είναι ένα στοιχείο που αποκτά αυτήν την ιδιότητα με το να θέσουμε display:flex; σε αυτό.
Το flex container μπορεί να εμπεριέχει διάφορα flex items, τα οποία είναι στοιχεία εντός αυτού και μπορούμε να αναφερθούμε σε αυτά ως απογόνους του. Επίσης, οποιοδήποτε στοιχείο μπορεί να είναι και flex container και flex item ταυτόχρονα. Αυτό είναι κάτι που χρησιμοποιείται συχνά όταν έχουμε να κάνουμε με σύνθετα layouts.
Εντός ενός flex item μπορούμε να χρησιμοποιήσουμε την εντολή flex, π.χ. flex: 1;. Είναι μια shorthand εντολή (δηλαδή μία εντολή που θέτει πολλαπλές ιδιότητες της CSS ταυτόχρονα) για τις flex-grow, flex-shrink και flex-basis.
Το flex-grow αφορά το πόσο παραπάνω χώρο θα καταλάβει ένα flex item και, πιο συγκεκριμένα, το κατά πόσο θα μεγεθυνθεί σε σχέση με τα υπόλοιπα. Άμα, π.χ., θέσουμε το flex-grow ως 1 σε ένα στοιχείο, θα καταλάμβανε τον ίδιο χώρο με τα υπόλοιπα εντός του ίδιου flex container, ενώ άμα έπαιρνε την τιμή 2 θα είχε το διπλάσιο μέγεθος σε σχέση με αυτά, άμα ήταν 3 θα είχε το τριπλάσιο και πάει λέγοντας.
Το flex-shrink είναι παρόμοιο με το flex-grow αλλά με τη διαφορά ότι συρρικνώνει το στοιχείο και ενεργοποιείται μόνο όταν το συνολικό μέγεθος των flex items είναι μεγαλύτερο από το μέγεθος του flex container.
Άμα δε θέλω ένα αντικείμενο να μικρύνει, μπορώ να θέσω σε αυτό flex-shrink: 0;. Γενικά, τα flex-grow και flex-shrink μπορούν να μην τηρήσουν τιμές width που μπορεί να έχω θέσει προηγουμένως.
Όσον αφορά το flex-basis, αυτό θέτει το αρχικό μέγεθος ενός flex item έτσι ώστε τα flex-grow και flex-shrink να ξεκινάνε απ’ αυτό.
Μπορούμε να το θέσουμε ως pixels (αλλά όχι μόνο) και η default τιμή του είναι auto, όπου τότε το flex item ελέγχει για δήλωση width και την τηρεί. Μπορούμε να θέσουμε ταυτόχρονα τιμή σε αυτές τις εντολές μέσω της flex, π.χ., flex: 2 1 auto;, που ισούται με flex-grow: 2;, flex-shrink: 1; και flex-basis: auto;.
Η default τιμή του flex είναι flex: 0 1 0%;, δηλαδή flex-grow: 0;, flex-shrink: 1; και flex-basis: 0%;. Άμα θέσουμε μία μοναδική τιμή στο flex, π.χ. flex: 1;, αυτή θα λειτουργήσει μόνο στο flex-grow, π.χ. το flex: 1; αντιστοιχεί στο flex: 1 1 0%;.
Flex-direction
Μια άλλη βασική ιδιότητα του flexbox είναι η δυνατότητα κατανομής στοιχείων είτε στον Χ άξονα, δηλαδή οριζόντια, είτε στον Υ άξονα, δηλαδή κάθετα. Αυτή η επιλογή μπορεί να γίνεται μέσω της εντολής flex-direction. Η default τιμή της είναι η flex-direction: row;, όπου εκεί το ένα flex item θα βρίσκεται δίπλα στο άλλο. Άμα, από την άλλη, τη θέσουμε ως flex-direction: column;, τα flex items θα κατανεμηθούν το ένα κάτω από το άλλο. Όταν αλλάζουμε το flex-direction σε column, αλλάζει ο τρόπος με τον οποίο λειτουργούν μερικές εντολές που ενεργούν με βάση το άμα βρισκόμαστε στον Χ ή στον Υ άξονα. Π.χ., το flex-basis θα αναφέρεται πλέον στο height του στοιχείου αντί στο width.
Επιπλέον, το flex-direction μπορεί να πάρει και τις τιμές row-reverse και column-reverse, με τις οποίες αλλάζει η σειρά των flex items έτσι ώστε να αντιστρέφονται η αρχή και το τέλος της γραμμής και της στήλης αντίστοιχα.

Justify-content και align-items
Το flexbox μας δίνει, επίσης, τη δυνατότητα να τοποθετούμε flex items με συγκεκριμένο τρόπο εντός ενός flex container μέσω των εντολών justify-content και align-items που ενεργούν επί τον άξονα Χ και Υ αντίστοιχα.
H default τιμή του justify-content είναι η flex-start, όπου τα flex items κολλάνε στην αριστερή μεριά του flex container.
Αντίστοιχα, έχουμε και το flex-end, όπου τότε τα flex items κολλάνε στη δεξιά μεριά του flex container, και το center, όπου τότε τοποθετούνται στο κέντρο.
Αυτή η εντολή μπορεί να πάρει και άλλες τιμές, π.χ., θέτοντας justify-content: space-between;, τα flex items θα χωρίζονται με ισόποση απόσταση μεταξύ τους καθώς εξαπλώνονται από το ένα άκρο του flex container ως το άλλο.
Δύο άλλες τιμές που μπορεί να πάρει είναι το space-around, που είναι το ίδιο με το space-between αλλά με τη διαφορά ότι προστίθεται κενό και στην αρχή και τέλος του flex container, και το space-evenly, όπου όλα τα flex items θα έχουν ισόποσο κενό τριγύρω τους.
Όσον αφορά το align-items, παίρνει τις ίδιες τιμές και γενικά δουλεύει με τον ίδιο τρόπο που δουλεύει το justify-content με τη διαφορά ότι λειτουργεί κάθετα και όχι οριζόντια. Για παράδειγμα, μέσω του align-items: start; τα flex items κολλάνε προς τα πάνω.
Η default τιμή του align-items είναι η stretch, με βάση της οποίας το ύψος των flex items επεκτείνεται ώστε να καταλαμβάνει όσο περισσότερο χώρο γίνεται.
Εδώ είναι σημαντικό να θυμόμαστε ότι τα justify-content και align-items βασίζονται στον άξονα του flex container, που σημαίνει ότι η συμπεριφορά τους αντιστρέφεται όταν αλλάζω το flex-direction σε column. Τότε, το justify-content: start; θα τοποθετούσε τα flex items προς τα πάνω αντί για προς τα αριστερά, για παράδειγμα.
Υπάρχουν, επιπλέον, και οι εντολές justify-self και align-self, που έχουν αντίστοιχη λειτουργία με τις justify-content και align-content με τη διαφορά ότι ενεργούν σε μοναδικά flex items και όχι σε όλα εντός του flex container.
Gap
Μία άλλη ιδιότητα που συχνά χρησιμοποιείται στο flexbox είναι το gap.
Το gap, η οποία καθορίζει την απόσταση που θα έχουν μεταξύ τους τα flex items, π.χ. gap: 10px; (μπορεί να πάρει και άλλες τιμές, όπως em ή ποσοστά). Υπάρχουν και οι εντολές column-gap και row-gap, που με ανάλογο τρόπο καθορίζουν την απόσταση που έχουν οι στήλες και οι γραμμές των flex items αντίστοιχα. Ένας εναλλακτικός τρόπος για να ορίσουμε απόσταση ξεχωριστά σε στήλες και γραμμές είναι θέτοντας δύο τιμές στην gap. Η πρώτη τιμή θα αναφέρεται στις γραμμές και η δεύτερη στις στήλες, για παράδειγμα, η εντολή gap: 5px 10px; ισούται με row-gap: 5px; και column-gap: 10px;.
Flex-wrap
Μία ακόμα χρήσιμη ιδιότητα του flexbox που οφείλουμε να αναφέρουμε είναι το flex-wrap. Αυτή η ιδιότητα καθορίζει το άμα τα flex items ενός flex container θα παραμείνουν στην ίδια γραμμή είτε χωράνε είτε όχι ή άμα χωριστούν στην από κάτω γραμμή. Η default τιμή του flex-wrap είναι το nowrap, όπου τα flex items παραμένουν στην ίδια γραμμή. Θέτοντας flex-wrap: wrap; θα χωριστούνε πηγαίνοντας στην από κάτω γραμμή, ενώ θέτοντας flex-wrap: wrap-reverse; θα πάνε στην από πάνω γραμμή.
Μία ακόμα εντολή που θα ταίριαζε να αναφέρουμε εδώ είναι η flex-flow, η οποία συνδυάζει το flex-direction και το flex-wrap λαμβάνοντας μία τιμή για το καθένα. Μπορούμε, π.χ., να χρησιμοποιήσουμε το flex-flow: row wrap; αντί για τα flex-direction: row; και flex-wrap: wrap;.
Κατακλείδα
Συνοψίζοντας, το flexbox είναι ένας ιδιαίτερα βολικός τρόπος για να τοποθετήσουμε όπως θέλουμε διάφορα στοιχεία στον χώρο χρησιμοποιώντας CSS.
Οι διάφορες ιδιότητες που σχετίζονται με αυτό μπορούν να κάνουν αυτήν τη δουλειά πιο εύκολη σε σχέση με άμα δεν το χρησιμοποιούσαμε, ειδικά άμα πρόκειται για τοποθέτηση στοιχείων στο κέντρο. Άλλοι τρόποι με τους οποίους θα μπορούσαμε να τοποθετήσουμε στοιχεία στον χώρο είναι τα float και grid.