Search code examples
htmlcsslayoutcss-selectorscss-grid

Why are some grid items appearing out of order?


I am working on a CSS grid layout that looks something like this: https://jsfiddle.net/ftL5zw0x/23/ where I don't know how many items I will have.

The layout looks how I want it to but the problem is with the ordering. Every 6th and 7th items appear out of order, they should switch places while the layout stays unchanged. (For example items 6 and 7)

Is there any way I can achieve this through CSS alone?

.wrapper {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  grid-auto-rows: 100px;
  grid-gap: 8px;
}

.item {
  background-color: #c4c4c4;
  display: flex;
  justify-content: center;
  align-items: center;
}

div:nth-child(8n+1),
div:nth-child(8n+3), 
div:nth-child(8n+7),
div:nth-child(8n+8) {
  grid-row: span 1;
}

div:nth-child(8n+2), 
div:nth-child(8n+4),
div:nth-child(8n+5), 
div:nth-child(8n+6) {
  grid-row: span 2;
}
<div class="wrapper">
  <div class="item">item1</div>
  <div class="item">item2</div>
  <div class="item">item3</div>
  <div class="item">item4</div>
  <div class="item">item5</div>
  <div class="item">item6</div>
  <div class="item">item7</div>
  <div class="item">item8</div>
  <div class="item">item9</div>
  <div class="item">item10</div>
  <div class="item">item11</div>
  <div class="item">item12</div>
  <div class="item">item13</div>
  <div class="item">item14</div>
  <div class="item">item15</div>
  <div class="item">item16</div>
</div>


Solution

  • First change your selectors that is the 7th element that should span not the 6th

    This will push the 6th element to the right following the flow of the grid that is being the position of the previous element 5th

    However we can enforce the position of every 6th element because we know it's the second column.

    That will make the 7th and 8th element follow the 6th element we can fix this with grid-auto-flow:row dense;

    .wrapper {
      display: grid;
      grid-template-columns: repeat(4, 1fr);
      grid-auto-rows: 100px;
      grid-auto-flow: row dense;
      grid-gap: 8px;
    }
    
    .item {
      background-color: #c4c4c4;
      display: flex;
      justify-content: center;
      align-items: center;
    }
    
    div:nth-child(8n+1),
    div:nth-child(8n+3),
    div:nth-child(8n+6),
    div:nth-child(8n+8) {
      grid-row: span 1;
    }
    
    div:nth-child(8n+2),
    div:nth-child(8n+4),
    div:nth-child(8n+5),
    div:nth-child(8n+7) {
      grid-row: span 2;
    }
    
    div:nth-child(8n+6) {
      grid-column: 2;
    }
    <div class="wrapper">
      <div class="item">item1</div>
      <div class="item">item2</div>
      <div class="item">item3</div>
      <div class="item">item4</div>
      <div class="item">item5</div>
      <div class="item">item6</div>
      <div class="item">item7</div>
      <div class="item">item8</div>
      <div class="item">item9</div>
      <div class="item">item10</div>
      <div class="item">item11</div>
      <div class="item">item12</div>
      <div class="item">item13</div>
      <div class="item">item14</div>
      <div class="item">item15</div>
      <div class="item">item16</div>
    </div>