{
"$type": "site.standard.document",
"content": {
"$type": "at.markpub.markdown",
"text": {
"$type": "at.markpub.text",
"markdown": "CSS Frameworks like Bootstrap, Foundation, and Bulma help us describe our HTML in terms of layout structure and components, but I'm not a fan of that approach.\n\nI prefer an approach I learned from [Jen Simmons](https://www.youtube.com/watch?v=qNtJ5p3h2A4) where HTML is used to describe the actual content of the page. Layout doesn't ever factor into it. After all, it is _markup_ so it should be used to add semantic meaning to your content. But aside from this philosphical interpretation there are other reasons to not bake layout into your HTML.\n\nA big one is there are fewer `div`s cluttering up the DOM which can improve performance. And it also results in cleaner looking code since there are fewer utility-classes in the HTML (though this last one is subjective as frameworks like [Tailwind CSS](https://tailwindcss.com/) make a reasonable argument for more of these utility-classes in your HTML).\n\n- [View Demo App](https://arkmuntasser.github.io/css-grid-demos/)\n- [Download Source Code on GitHub](https://github.com/arkmuntasser/css-grid-demos)\n\n## Prerequisites\n\n- Working knowledge of [HTML and CSS](https://internetingishard.com/html-and-css/)\n- Familiarity with [Responsive Web Development](https://www.smashingmagazine.com/2011/01/guidelines-for-responsive-web-design/)\n\n## Rethinking your HTML\nLet's consider this following layout:\n\n\n\nUsing Foundation, I might write some HTML like this:\n\n```html\n<section class=\"articles\">\n <div class=\"row\">\n <div class=\"columns large-8\">\n <div class=\"row\">\n <div class=\"columns large-6\">\n <article><!-- content --></article>\n </div>\n <div class=\"columns large-6\">\n <article><!-- content --></article>\n </div>\n </div>\n </div>\n <div class=\"columns large-4\">\n <article><!-- content --></article>\n <article><!-- content --></article>\n </div>\n </div>\n <div class=\"row\">\n <div class=\"columns large-8\">\n <article><!-- content --></article>\n </div>\n <div class=\"columns large-4\">\n <article><!-- content --></article>\n </div>\n </div>\n</section>\n```\n\nThis is fine, but what is this thing? Really? It's just a list of articles, right? So shouldn't the HTML just look like this:\n\n```html\n<section class=\"articles\">\n <article><!-- content --></article>\n <article><!-- content --></article>\n <article><!-- content --></article>\n <article><!-- content --></article>\n <article><!-- content --></article>\n <article><!-- content --></article>\n</section>\n```\n\n## Add in the CSS\n\nThat's a lot cleaner looking and a lot more descriptive of the content we have. But now that we've gotten rid of the layout, how do we add it back in? That's where CSS Grid comes in!\n\n### Example 1\n```css\n.articles {\n display: grid;\n grid-template-columns: 5fr 5fr 4fr;\n grid-template-rows: repeat(6, 7vw);\n grid-gap: 1rem;\n}\n.articles article {\n grid-column: span 1;\n grid-row: span 3;\n}\n.articles article:nth-child(3) {\n grid-row: span 1;\n}\n.articles article:nth-child(4) {\n grid-row: span 2;\n}\n.articles article:nth-child(5) {\n grid-column: span 2;\n}\n```\n\nThat's it! That's all the CSS that you need to recreate the layout. I find this to be far easier to read than the framework-based solution above.\n\nSo now we've cleaned up our HTML and more accurately and concisely describe the actual content we have and we we're able to move our layout logic into just a few lines of CSS. But we haven't even gotten to the best part!\n\nBecause we're now handling layout in the CSS, we can take our simplified HTML and display it nearly anyway that we want without altering it!\n\n### Example 2\nWhat if we change our CSS to this:\n\n```css\n.articles {\n display: grid;\n grid-template-columns: 1fr 1fr 1fr;\n grid-template-rows: repeat(18, 6vw);\n list-style: none;\n}\n.articles article:nth-child(1) {\n grid-column: 1 / span 2;\n grid-row: 1 / span 3;\n}\n.articles article:nth-child(2) {\n grid-column: 2 / span 2;\n grid-row: 3 / span 3;\n}\n.articles article:nth-child(3) {\n grid-column: 1 / span 2;\n grid-row: 5 / span 3;\n}\n.articles article:nth-child(4) {\n grid-column: 2 / span 2;\n grid-row: 7 / span 3;\n}\n.articles article:nth-child(5) {\n grid-column: 1 / span 2;\n grid-row: 9 / span 3;\n}\n.articles article:nth-child(6) {\n grid-column: 2 / span 2;\n grid-row: 11 / span 3;\n}\n```\n\nAnd get this:\n\n\n\n### Example 3\nOr maybe we want something a little wilder?\n\n```css\n.articles {\n display: grid;\n grid-template-columns: repeat(5, 1fr);\n grid-template-rows: repeat(3, 19vw);\n}\n.articles article {\n grid-column: span 1;\n grid-row: span 1;\n}\n.articles article:nth-child(2) {\n grid-column: 3;\n}\n.articles article:nth-child(3) {\n grid-column: 5;\n}\n.articles article:nth-child(4) {\n grid-column: 2;\n}\n.articles article:nth-child(5) {\n grid-column: 4;\n}\n.articles article:nth-child(6) {\n grid-column: 3;\n}\n```\n\n\n\n### Example 4\nMaybe something a bit more standard?\n\n```css\n.articles {\n display: grid;\n grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));\n grid-gap: 2rem 1rem;\n}\n.articles article {\n height: 19vw;\n}\n```\n\n\n\n## Conclusion\nAcross all these layouts, there's only maybe 12 lines of CSS that's different. That's the power of CSS Grid and the power of moving layout out of the HTML."
}
},
"description": "HTML is for structuring and describing your content and not for layout.",
"path": "/posts/write-better-code-with-css-grid",
"publishedAt": "2018-02-11T00:00:00.000Z",
"site": "at://did:plc:2lm4lab5fhnj6kaazrxopv37/site.standard.publication/self",
"tags": [
"css-grid",
"layout",
"design",
"clean-code",
"html"
],
"title": "Write Better Code with CSS Grid"
}