I really enjoyed reading this article by Alex Riviere and found myself nodding along in places. I do disagree with the overall approach though because I come at layout from a different angle. I’m very much in the “layout should be a skeletal, flexible system” camp and have articulated it lot over the years. My CUBE CSS article will get you up to speed with my ideals if you’ve not seen any of that though.
I need to emphasise that I don’t think Alex is wrong in their writing, just to be clear. Their lived experience and response to that experience is completely valid — as is yours based on your own experience, dear reader.
The beauty of CSS is that it’s flexible — it wants to be a system — so finding a solution that works for you and your team is ultimately the most important thing.
Where I’m atpermalink
When we wrote Every Layout back in 2019, Heydon and I were both trying to come up with systems that essentially let the browser do the work for you. The reason for that is you don’t know what a user’s browser is going to do with your UI and you certainly don’t know what viewport size a user is visiting with either.
Our approach from Every Layout sets layouts up to be content driven and to respond to high level rules that can be broken when the browser decides that they need to be, based on the parameters of those rules.
Having said that, I know being the browser’s mentor, not its micromanager isn’t for everyone, so here’s my take on some rules of thumb that hopefully work for most people.
You’re comfortable if you feel like you have complete controlpermalink
If this is you, I would recommend using media queries and/or container queries to control grid-based layouts. CSS grid is likely the right tool for the job here because it is by nature, a very rigid and solid layout system.
- Code language
- css
.my-layout { display: block } .my-layout__child:not(:last-child) { margin-block-end: 1em; } @media (width > 750px) { .my-layout { display: grid; grid-template-columns: repeat(3, 1fr); gap: 1em; } .my-layout__child:not(:last-child) { margin-block-end: revert; } }
Toggle the HTML or CSS panel to see the layout snap to a stacked layout.
See the Pen Simple media query layout by piccalilli (@piccalilli) on CodePen.
Maintaining that complete control you desire with flexbox is going to be hard, as Alex rightly mentions in their article. That’s because flexbox is a flexible layout system (the clue is in the name). By setting specific widths on flex children, you’re going against the grain of that flexible layout system, so as I see it, reaching for grid will only help here if perceived, ultimate control is what you want.
You’re comfortable setting high level rules and letting the browser do the restpermalink
Hey that’s me! Almost all the layouts we authored for Every Layout are flex-basis
powered. This property is not necessarily “be this exact width”, to be clear. It’s more “look, this is the ideal width we’re aiming for, but use that as a reference and you work out what’s best, based on your current situation and the other parameters I’ve given you, your siblings and your parent”. The flex-basis
property gives flexible layouts a basis of control to work around too while providing that ever-so-useful escape hatch.
A good example of this setup is the sidebar layout. You set an ideal sidebar width (flex-basis
) and allow its sibling to grow. You also set a minimum content width for that same sibling to avoid everything being too squished up.
Again, toggle the HTML or CSS panel to see the layout snap to a stacked layout.
See the Pen Simple sidebar layout by piccalilli (@piccalilli) on CodePen.
It’s all about simple rules that allow the browser to do its work. This system works better if you treat layout as a skeletal system, like in CUBE CSS compositions too.
Your layout needs are multi-dimensional and/or very specificpermalink
It’s time to get grid out again. Just like the first scenario, you need control here so grid is the right tool for that.
The header on this website is a good example of that scenario. Almost all of the layout on this website is flexible and flexbox-based, but for layouts like that header — which has very specific child element positioning — CSS grid does the job really nicely for us.
On the flip side however, that same header is a refactor/design refresh target because although it looks great, it’s becoming quite cumbersome as this platform evolves. CSS grid is great for giving you control for your immediate circumstances, but in my experience it can make iterating and evolving quite difficult in the longer term.
I’ve got to say that named areas really help eradicate those scaling issues though.
Above everything, don’t settle for absolutespermalink
I often paraphrase Rachel Andrew:
If it works, it’s right
Heck, I even titled this article as if it works, it’s right! I can’t for the life of me remember when or where I heard Rachel say that — I feel like it might have been when we were working on Learn CSS together — but her wisdom bounces around in my brain like reverb.
I find it very hard to say to people “do X like this because it is the right way” because I don’t know their circumstances, I don’t know their codebase and I certainly don’t know their organisation’s goals and ideals. All I can do is what I’ve done in this article, in my course and in my teaching in general: give people advice and methodologies to work from and let them find their own path.
Some people like to be told exactly how to do stuff, and to those people, I’d say go and read Alex’s article again because their approach is really sound. I can see it being a solid method of tackling CSS layout for sure. It’s just not to my taste, and that’s fine.
Most importantly, you do you and if you’re in a team, you and your team do what works well for you all. That’s the only right answer — especially when it comes to writing good CSS.