Responsive CSS Layouts WITHOUT Media Queries
Tags: css, webdev, flexbox, grid
Published: 2020-01-21 17:13:32

---
title: Responsive CSS Layouts WITHOUT Media Queries
published: true
description: Using Flexbox and Grid to create responsive layouts, with fewer lines of CSS!
tags: css, webdev, flexbox, grid
canonical_url: https://dev.to/kylefilegriffin/responsive-css-without-media-queries
cover_image: https://thepracticaldev.s3.amazonaws.com/i/6gw3r7t9d4xjyas5yz7x.png
---

The introduction of Media Queries to the CSS specification in 2012 was the beginning of an age of Responsive Web Development. With CSS getting more and more comprehensive, we could now roll out completely different looks at certain breakpoints, on certain devices and even if the user had their phone on landscape!

When learning CSS, it is highly recommended to build your site and get it to a place where you are happy with its desktop layout, then to add in media queries to affect page elements as the browser's width reduces to the width of a mobile phone screen. I build to account for screens as narrow as 320 pixels; the width of the iPhone 4/iPhone SE.

But what if, you could create completely responsive layouts, starting from desktop and intelligently allocating itself space on the page when it starts to get too narrow? 

## Flex - When your elements vary

Let's take a form of inputs as an example. Some inputs are going to require a long string of text from the user, with a high amount of variance, such as an Email Address. Some are not so long, such as a name field. If elements can fit on the same line, then you would want them to, especially if the inputs are contextual to each other in the form. Then they become full width on their own line if the available screen width starts to narrow.

{% codepen https://codepen.io/kylegriffin/pen/LYEgZrG %}

Resize your screen, change your screen's orientation on mobile, or open up the HTML/CSS tab to narrow the form width. You'll see that the inputs move to their own line!

The secret is the power of **flex: auto**. 

```css
input {
  max-width: 100%;
}

input.fill {
  flex: 1 0 auto;
}

input#fname {
  flex: 1 0 240px;
}

input#email {
  flex: 1 0 350px;
}
```

With `flex-wrap: wrap` set onto the container, the child elements will attempt to drop down to a new line once it gets too narrow. If no breakpoint has been set, then it will use its content and padding to determine it's minimum width. 

In this example, the telephone field and the submit button are both set to `flex: auto`, attached to the class name `fill`. The name and email set with pixel widths via `flex-basis`, the third value of the `flex` shorthand. This width is the basis for which it can determine that it will grow to full width (set by the 1 in `flex: 1 0 ___px`) if the space is available to do so.

And finally, setting `max-width: 100%` will prevent all inputs from exceeding the width of the container. Quite unsightly!

So, as long as you know what elements will be last on their line, you can allow the first element on the line to determine when you want everything to drop onto its own line. Pretty neat!


## Grid - When your elements don't vary

Grid is the cool kid on the block. Flexbox fanatics are scared of it, but I find it sneaking it's way into many different solutions to common problems when building websites. In this case, it can also allow for a responsive layout, but with fewer lines of code than flexbox.

Grid works exceptionally well when all the items you want to make responsive are of equal width and size, like a gallery of images or a grid of blog posts.

You can achieve this layout with a complicated-looking `grid-template-columns`

```css
.grid {
   display: grid;
   grid-template-columns: repeat(auto-fill, minmax(250px, 1fr));
}
```

(The 250px can be set to allow more columns to fit onto a single line at once. You can even set it to `rem` if you want to change the minimum size with media queries later)

- `repeat` applies this resizing logic to all grid items
- `auto-fill` attempts to fill up the grid row. `auto-fit` will ignore the container's full width and look at the minimum width of the item instead. Both are worth using for different situations! For a more in depth look at this, read [Sara Soueidan's article on CSS Tricks](https://css-tricks.com/auto-sizing-columns-css-grid-auto-fill-vs-auto-fit/)
- `minmax` allows you to decide what is the minimum and maximum width that the grid item can have. In my example, it can be as narrow as 250px and as wide as the container will allow. Since only 2 items can fit at 500px, at 450px a single item will stretch the entire width.

The main advantage over flexbox here is the inclusion of `grid-gap` which removes a lot of stress with creating whitespace around your grid items. Bootstrap likes to have a gap of 15px around it's columns, but I feel that working in multiples of 8 is easier to scale upwards depending on your page content.

{% codepen https://codepen.io/kylegriffin/pen/povqvRq %}

If CSS Grid is absolutely alien to you but you're eager to dive into it, I strongly recommend bookmarking [Grid by example by Rachel Andrew](https://gridbyexample.com/) and following [Her on Twitter](https://twitter.com/rachelandrew). 

### Flex is for when grid isn't suitable

At this moment in time, the CSS grid spec struggles to "auto-fill" individual grid items. `grid-column` allows you to span your grid item an unfixed number of columns, but it does not take into account other items on the same line. If you know where your dynamic grid item will start will, then you can do...

```css
.grid-item {
  grid-column: 4 / -1;
}
```

which will stretch the item to the end of the line from the 4th column. But as you can see, you would have to be aware of explicit grid item(s) previously on the same line. That's not at all responsive!

Thanks for reading!