काही वर्षांपूर्वी, मी एक डॅशबोर्ड बनवण्यास सुरुवात केली. काही विशेष नाही—फक्त एक फिक्स्ड साइडबार, एक मुख्य कंटेंट एरिया आणि एक फुटर. Flexbox हा एक सोपा पर्याय वाटत होता आणि सुरुवातीला तो व्यवस्थित काम करत होता. पण जेव्हा मी मुख्य सेक्शनमध्ये कार्ड्सची एक रांग टाकली, तेव्हा संपूर्ण लेआउट विस्कळीत झाला. त्यानंतर मी पुढची तीन तास flex-grow रेशिओ आणि नेस्टेड टक्केवारीच्या रुंदीशी (nested percentage widths) झुंज देत घालवली; कितीही पॅडिंग कमी केले तरी कंटेनर्स एका ओळीत येण्यास नकार देत होते. ते पेज एखाद्या कोसळणाऱ्या टॉवरसारखे वाटत होते.

त्या कठीण अनुभवाने मला आधुनिक CSS लेआउटबद्दलची सर्वात महत्त्वाची गोष्ट शिकवली: Flexbox आणि Grid हे एकमेकांचे प्रतिस्पर्धी नाहीत. ते वेगवेगळ्या कामांसाठी असलेली साधने आहेत, आणि बहुतेक अयशस्वी लेआउट्स चुकीचे साधन निवडल्यामुळेच होतात.

फरक आयामाचा (Dimensional) आहे

Flexbox ला एका गॅलरीसारखे (hallway) समजा. यामध्ये घटक एकाच दिशेने वाहतात, एक तर रो (row) म्हणून किंवा कॉलम (column) म्हणून. हे एक-आयामी (one-dimensional) वितरणासाठी बनवले आहे. ब्राउझर कंटेंट पाहतो आणि मग त्या एका अक्षावर (axis) तो कसा ताणायचा, लहान करायचा किंवा अलाइन करायचा हे ठरवतो. यामुळे ज्या ठिकाणी कंटेंटनुसार लेआउट ठरवायचा असतो, तिथे Flexbox अगदी योग्य ठरते. नेव्हिगेशन बार, फॉर्म फील्ड्सचा संच किंवा समान अंतर हवे असलेले टॅग्स—हे सर्व Flexbox कंटेनरमध्ये नैसर्गिकरित्या बसतात कारण त्या सर्वांचे लॉजिक एकाच ओळीवर असते.

दुसरीकडे, Grid म्हणजे एखाद्या घराचा फ्लोअर प्लॅन आहे. हे काटेकोरपणे दोन-आयामी (two-dimensional) असते, जे रो आणि कॉलम दोन्ही एकाच वेळी हाताळते. तुम्ही प्रथम रचना (structure) ठरवता आणि मग त्यामध्ये घटक ठेवता. यामुळे संपूर्ण पेज आर्किटेक्चरसाठी Grid आदर्श ठरते—जिथे तुम्हाला व्हर्टिकल आणि हॉरिझॉन्टल पोझिशनिंग दोन्ही एकत्र नियंत्रित करायचे असते. जेव्हा तुम्ही नेस्टेड Flexbox कंटेनर्सद्वारे एखादा जटिल दोन-आयामी डिझाइन तयार करण्याचा प्रयत्न करता, तेव्हा शेवटी तुम्हाला खूप जास्त मार्काप (markup), नाजूक रॅपर्स आणि क्लिष्ट गणिती प्रक्रिया यांचा सामना करावा लागतो, जे एक अतिरिक्त घटक जोडताच कोलमडून पडते.

Flexbox अजूनही तितकेच महत्त्वाचे आहे

प्रत्येक Flex कंटेनरला Grid ने बदलण्याची घाई करू नका. वैयक्तिक घटकांच्या (individual components) आत Flexbox अनेकदा अधिक सुटसुटीत आणि प्रभावी असते. जर तुमच्याकडे दोन बटणांसह एक कार्ड फुटर असेल आणि तुम्हाला एक डावीकडे आणि दुसरे उजवीकडे अलाइन करायचे असेल, तर justify-content: space-between अगदी तंतोतंत काम करते. जर तुम्हाला अज्ञात उंचीच्या बटणांतर्गत एखादा आयकॉन व्हर्टिकली सेंटर करायचा असेल, तर align-items: center हा सर्वात सोपा मार्ग आहे. बदलणारा कंटेंट—जसे की वेगवेगळ्या लांबीच्या नावांसह युजर बॅजेसची रांग—Flexbox मध्ये सहज बसतो कारण ते 'कंटेंट-फर्स्ट' (content-first) आहे. कंटेनर त्याच्यामध्ये असलेल्या कंटेंटनुसार स्वतःला जुळवून घेतो.

Grid हे 'कंटेनर-फर्स्ट' (container-first) आहे. तुम्ही ब्राउझरला किती ट्रॅक्स आहेत आणि त्यांची साईज किती असावी हे सांगता आणि मग त्या सेल्समध्ये घटक टाकता. जर तुमचा लेआउट फक्त एकाच ओळीतील घटकांसाठी असेल, तर Grid वापरणे अनावश्यक गुंतागुंत वाढवण्यासारखे आहे.

पेज लेआउटसाठी Grid वापरा

येथे Grid आपली ताकद दाखवते. माझा डॅशबोर्डचा तो nightmare आठवतोय? रचना सुरुवातीपासून अशी असायला हवी होती:

.page {
  display: grid;
  min-height: 100vh;
  grid-template-rows: auto 1fr auto;
  grid-template-columns: 200px 1fr;
}

.header { grid-row: 1; grid-column: 1 / -1; }
.sidebar { grid-row: 2; grid-column: 1; }
.main { grid-row: 2; grid-column: 2; }
.footer { grid-row: 3; grid-column: 1 / -1; }

येथे काय घडत आहे ते पहा. .page कंटेनर तीन रो आणि दोन कॉलम तयार करतो. auto मुळे पहिली रो हेडरमध्ये असलेल्या कंटेंटनुसार स्वतःची साईज ठरवते. मधली रो 1fr वापरून उपलब्ध असलेली सर्व शिल्लक जागा व्यापते. फुटर शेवटच्या रो मध्ये त्याच्या स्वतःच्या कंटेंटनुसार बसतो. दरम्यान, साइडबारची रुंदी 200 पिक्सेलवर लॉक केली आहे आणि मुख्य एरिया उरलेली जागा व्यापतो.

येथील प्लेसमेंट लॉजिक (placement logic) खरोखरच दिलासादायक आहे. हेडर कॉलम लाईन 1 पासून लाईन -1 पर्यंत पसरलेला आहे, याचा अर्थ तुम्ही नंतर कितीही कॉलम जोडले तरी ते दोन्ही कॉलममध्ये पसरलेले राहील. साइडबार आणि मुख्य कंटेंट रो 2 शेअर करतात पण वेगवेगळ्या कॉलममध्ये असतात. फुटर रो 3 मध्ये पूर्ण रुंदी घेतो. तुम्हाला चाइल्ड एलिमेंट्सवर टक्केवारीचे गणित करण्याची गरज नाही. उंचीसाठी नेस्टेड रॅपर्स वापरण्याचीही गरज नाही. फक्त एका ठिकाणी साइडबारची रुंदी बदला आणि मुख्य एरिया आपोआप ॲडजस्ट होईल. संपूर्ण लेआउट एकात्मिक प्रणालीप्रमाणे सहजपणे काम करतो.

grid-template-areas मुळे वाचनीयता वाढते

अधिक स्पष्टतेसाठी, तुम्ही तुमच्या सेक्शनना नावे देऊ शकता. लाईन नंबर मॅनेज करण्याऐवजी, तुम्ही एक व्हिज्युअल मॅप लिहू शकता:

.page {
  grid-template-areas:
    "header header"
    "sidebar main"
    "footer footer";
}

.header { grid-area: header; }
.main { grid-area: main; }

आता तुमची स्टाईलशीट एखाद्या वायरफ्रेमसारखी वाचता येईल. जर तुम्हाला एखाद्या वेगळ्या ब्रेकपॉइंटसाठी साइडबार उजव्या बाजूला दाखवायचा असेल, तर तुम्हाला फक्त टेम्पलेट स्ट्रिंगमधील दोन शब्द बदलावे लागतील. नेस्टेड Flex कंटेनर्सच्या ढिगाऱ्यात अशा प्रकारची स्ट्रक्चरल वाचनीयता मिळवणे अशक्य आहे.

दोन कठीण धडे

Grid ही जादू नाही. अशा दोन चुका आहेत ज्या तुमचा लेआउट पटकन बिघडवू शकतात.

पहिले म्हणजे युनिट्सचा अस्ताव्यस्त वापर. जर तुम्ही grid-template-columns: 1fr 1fr 1fr असे परिभाषित केले, परंतु तुमच्या डिझाइनला फक्त दोन कॉलमच्या कंटेंटची गरज असेल, तर तो तिसरा ट्रॅक तरीही अस्तित्वात राहतो. तो एकतर रिकामा राहील आणि तुम्ही अपेक्षित न केलेली पोकळी निर्माण करेल, किंवा तो तुमच्या मूळ कंटेंटला अशा प्रकारे कोंसण्यास भाग पाडेल ज्यामुळे तुमचे डिझाइन बिघडू शकते. विचारपूर्वक वापरा. जेव्हा तुम्हाला दोन कॉलम हवे असतील, तेव्हा repeat(2, 1fr) असे लिहा.