Web Development

2025 CSS Grid: 3 Lines for a 2-Row Auto-Fit Gallery

Tired of complex CSS for responsive galleries? Learn how to create a perfect 2-row, auto-fitting image gallery with just 3 lines of modern CSS Grid in 2025.

E

Elena Petrova

Frontend developer and CSS architect passionate about clean, efficient, and beautiful code.

6 min read19 views

2025 CSS Grid: 3 Lines for a 2-Row Auto-Fit Gallery

Let's be honest. For years, building the “perfect” responsive image gallery has felt like a dark art. We’ve wrestled with floats, clearing hacks, and flexbox trickery that worked… mostly. We’ve written more media queries than we care to admit, all in pursuit of a layout that looks great on a phone, a tablet, and a giant monitor.

What if I told you that for a huge number of common use cases, the solution is just three lines of CSS? No media queries. No container queries. No JavaScript. Just pure, modern CSS Grid.

By 2025, this isn't a futuristic dream; it's the standard. And today, I'm going to show you how to build a beautiful, responsive, 2-row gallery that just works.

The Old Ways vs. The Grid Way

Remember the pain? You'd float: left your gallery items and then pray you remembered to use a clearfix hack on the container. Then came flexbox, a massive leap forward! It gave us beautiful alignment and distribution, but creating a true two-dimensional, wrapping grid could still feel a bit… forced. Flexbox is fundamentally a one-dimensional system (either a row or a column).

CSS Grid, on the other hand, was built for this. It’s designed from the ground up to handle two-dimensional layouts. It understands rows and columns simultaneously, which is precisely what a gallery is.

The 3-Line Magic: Your New Favorite Snippet

First, let's look at the HTML. It's exactly as simple as you'd hope. A container (like a <div> or <section>) with your gallery items inside.

<section class="gallery">
  <div class="gallery-item"><img src="..." alt="..."></div>
  <div class="gallery-item"><img src="..." alt="..."></div>
  <div class="gallery-item"><img src="..." alt="..."></div>
  <div class="gallery-item"><img src="..." alt="..."></div>
  <div class="gallery-item"><img src="..." alt="..."></div>
  <div class="gallery-item"><img src="..." alt="..."></div>
</section>

Now, for the magic. Here are the only three lines of CSS you need to apply to the .gallery container:

.gallery {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));
  grid-template-rows: repeat(2, 25vw);
}

That’s it. Seriously. You now have a responsive gallery that will always have two rows. The number of columns will adjust automatically based on the screen width. No media queries needed.

Deconstructing the Code, Line by Line

It looks simple, but incredible power is packed into those three declarations. Let's break down exactly what each one is doing.

Line 1: display: grid;

Advertisement

This is our entry ticket. It flips the switch, turning our .gallery container into a grid formatting context. All its direct children (the .gallery-item divs) automatically become grid items, ready to be placed.

Line 2: grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));

This line is the heart of the responsive behavior. It's a dense but brilliant piece of code.

  • repeat(): This function saves us from writing out column definitions over and over. It says, “repeat the following pattern as many times as needed.”
  • auto-fit: This is where the magic happens. auto-fit tells the browser to create as many columns as will fit into the available space. If the columns don't fill the entire width, it will expand them to get rid of any empty space. It’s subtly different from its cousin, auto-fill, which would leave the empty space. For most gallery layouts, auto-fit is what you want for that clean, edge-to-edge look.
  • minmax(320px, 1fr): This function defines the size range for each column. It tells the browser, “Each column should have a minimum width of 320px. After that, if there’s extra space, share it equally, up to a maximum of 1fr (one fractional unit of the available space).”

Combined, this line creates a perfectly fluid and responsive column system. On a narrow screen, you might get one column. As the screen widens, it will automatically jump to two, three, four, or more columns, all without a single media query.

Line 3: grid-template-rows: repeat(2, 25vw);

This is the secret to our 2-row constraint. While the columns are flexible and automatic, the rows are explicit.

  • repeat(2, ...): This part explicitly tells the grid, “Create exactly two rows.” This is a hard rule. The grid will not create a third or fourth row on its own.
  • 25vw: This sets the height of each of our two rows. I've used 25vw (25% of the viewport width) to make the rows themselves responsive in height—they'll be taller on wider screens and shorter on narrower ones, maintaining their aspect ratio. You could easily use a fixed value like 300px or another responsive unit like rem depending on your design needs.

The “Catch”: When to Use This Technique

This technique is incredibly powerful, but it’s not a silver bullet for every gallery. It comes with one important consideration: it's designed for a known and limited number of items.

Because we explicitly defined two rows with grid-template-rows, the grid container has a fixed capacity. For example, if your layout shows 3 columns on desktop, your grid has space for 3 columns * 2 rows = 6 items. If you put 7 or 8 items in the HTML, they will overflow the grid container. They won't wrap to a new line because you've told the grid not to create any more rows.

Key Takeaway: Use this 3-line method for components where you control the number of items, such as a “Featured Products” section, a team bio page, or a “Latest Articles” widget.

This is perfect for things like:

  • A homepage hero showing your 4 main services.
  • An e-commerce section displaying 6 sale items.
  • A portfolio preview with your best 8 projects.

The Alternative: For Galleries with Unlimited Items

So what do you do when you have a gallery with an unknown number of items, like a user-generated photo album? You just make one tiny change to our recipe.

Instead of defining the rows with grid-template-rows, you define the height of implicitly created rows with grid-auto-rows.

.unlimited-gallery {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));
  grid-auto-rows: 25vw; /* The only change is here! */
}

With grid-auto-rows, the grid will use our responsive column setup and then create as many new rows as it needs to fit all the items, making each one 25vw tall. This gives you the classic, infinitely-scrolling gallery behavior.

Conclusion: The Right Tool for the Job

The “3-Line, 2-Row Gallery” isn't a hack; it's a testament to the power and precision of CSS Grid. It solves a very common design problem with an elegance and simplicity we could only have dreamed of a few years ago.

By understanding the difference between defining explicit tracks with grid-template-* and setting rules for implicit tracks with grid-auto-*, you unlock a new level of control over your layouts.

So next time you're building a featured content section, reach for this snippet. Your CSS file will thank you, and you'll have more time to focus on what really matters: creating amazing experiences on the web.

Tags

You May Also Like