Search code examples
htmlcssflexboxcenteringcss-grid

CSS Grid Column Stretch to Fill Entire Row / Or Centered In Row?


I have a basic grid setup as follows:

.grid-container {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(33rem, 1fr));
  grid-gap: 1rem;
}

When the grid auto-breaks into new rows, I either want the elements on the new rows to take up a proportional amount of space or be centered so that they look nice.

For example, if I have 3 elements in one row, then I want each to take up 33% of the container space. But when the grid breaks and only 1 element is on the new row, I want that element to either take up 100% of the row width, or at least look centered -- which is contrary to the default behavior of placing the element all the way to the left and taking up only 1fr of space.

Similarly, if there are 2 elements on the new row, then each should take up 50% of the row space or the two together should look centered.

I don't know how many elements there will be in total. Ideally, the solution should work for a minimum of 1 up to an arbitrary number of elements.

If anyone has any ideas, please let me know. Thanks.


Solution

  • This is a job for flexbox, I don't think it will be easy to achieve with CSS grid:

    .grid-container {
      display: flex;
      flex-wrap:wrap;
      border:1px solid;
      margin:2px;
    }
    
    .grid-container>div {
      height: 50px;
      background: red;
      margin: .5rem;
      flex: 1 1 calc(33% - 1rem);
    }
    <div class="grid-container">
      <div></div>
      <div></div>
      <div></div>
    </div>
    <div class="grid-container">
      <div></div>
      <div></div>
      <div></div>
      <div></div>
    </div>
    <div class="grid-container">
      <div></div>
      <div></div>
      <div></div>
      <div></div>
      <div></div>
    </div>

    If you want the element to be centred simply do this:

    .grid-container {
      display: flex;
      flex-wrap:wrap;
      border:1px solid;
      margin:2px;
      justify-content:center;
    }
    
    .grid-container>div {
      height: 50px;
      background: red;
      margin: .5rem;
      flex: 0 1 calc(33% - 1rem); /*disable the flex-grow*/
    }
    <div class="grid-container">
      <div></div>
      <div></div>
      <div></div>
    </div>
    <div class="grid-container">
      <div></div>
      <div></div>
      <div></div>
      <div></div>
    </div>
    <div class="grid-container">
      <div></div>
      <div></div>
      <div></div>
      <div></div>
      <div></div>
    </div>