5

edit: Not sure this is a duplicate? I don want the background color to extend past the width of the container, I want the container to expand to the size of its display: grid child. Updated the example to better explain my problem.

I am building a table where each row is a css grid. I have done this to leverage the minmax() of each cell, to make the whole table scrollable when its cells can't shrink anymore, while allowing the table to grow if more space is available.

This works fine besides the fact that the styling for the rows only apply to the width of the container.

Please see this example:

.container {
  width: 430px;
  background: grey;
  overflow-x: scroll;
}

.row {
  display: grid;
  grid-template-columns: minmax(200px, 1fr) minmax(200px, 1fr) minmax(200px, 1fr) minmax(100px, 1fr);
  background: red;
  height: 3rem;
  margin: 0.5rem;
}

.cell {
  border: 1px solid black;
}
Scroll to the right inside the box:
<div class="container">
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
</div>
Elements with the <code>.row</code> class should expand to fit all the cells.

Is there any way to solve this? I'm fine with adding extra elements if need be!

Amygdaloideum
  • 3,683
  • 2
  • 13
  • 16

2 Answers2

3

Changing the display of the rows to inline-grid seems to help:

.container {
  width: 430px;
  background: grey;
  overflow-x: scroll;
}

.row {
  display: inline-grid;
  grid-template-columns: minmax(200px, 1fr) minmax(200px, 1fr) minmax(200px, 1fr) minmax(100px, 1fr);
  background: red;
  height: 3rem;
}

.cell {
  border: 1px solid black;
}
Scroll to the right inside the box:
<div class="container">
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
</div>
The red background should cover the whole row.

Update 1

To avoid problems with wide container/narrow children getting in one line (as with the solution above), you can use a more convoluted solution, which uses a display: flex; flex-direction: column on the parent, with additional align-items: start that forces the row items to have full width (as opposed to default stretch, which makes the row width no wider than the container).

.container {
  width: 430px;
  background: grey;
  overflow-x: scroll;
  display: flex;
  flex-direction: column;
  align-items: start;
}

.container.container-wide{
  width: 1000px;
}

.row {
  display: grid;
  grid-template-columns: minmax(200px, 1fr) minmax(200px, 1fr) minmax(200px, 1fr) minmax(100px, 1fr);
  background: red;
  height: 3rem;
}

.cell {
  border: 1px solid black;
}
Scroll to the right inside the box:
<div class="container">
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
</div>
Wide container:
<div class="container container-wide">
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
</div>
The red background should cover the whole row.

Update 2

To allow for stretch of the row to the full width of the container in case it is wider than the sum of all columns, it is possible to adjust the solution from Update 1 by replacing the display: flex with display: grid, see example below:

.container {
  width: 430px;
  background: grey;
  overflow-x: scroll;
  display: grid;
}

.container.container-wide{
  width: 1000px;
}

.row {
  display: grid;
  grid-template-columns: minmax(200px, 1fr) minmax(200px, 1fr) minmax(200px, 1fr) minmax(100px, 1fr);
  background: red;
  height: 3rem;
}

.cell {
  border: 1px solid black;
}
Scroll to the right inside the box:
<div class="container">
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
</div>
Wide container:
<div class="container container-wide">
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
  <div class="row">
    <span class="cell">cell 1</span>
    <span class="cell">cell 2</span>
    <span class="cell">cell 3</span>
    <span class="cell">cell 4</span>
  </div>
</div>
The red background should cover the whole row.
Piotr Wicijowski
  • 1,975
  • 9
  • 15
  • The problem with this is that if the container becomes wide enough, the rows will end up next to each other. See this fiddle: https://jsfiddle.net/3n0ca6hy/ – Amygdaloideum Apr 14 '19 at 18:15
  • Added an update with a bit different solution that does not use `inline-*`, but rather a `display: flex` for the container. – Piotr Wicijowski Apr 14 '19 at 18:37
  • Thanks! But now the problem is that the table wont expand beyond the minimum width of the cells like it does without `align-items: start`. Maybe what I'm trying to achieve is impossible. – Amygdaloideum Apr 15 '19 at 08:11
  • I had one more go at the problem, see my updates. – Piotr Wicijowski Apr 15 '19 at 10:12
0

If you need to fill grid-template-columns with cell width, you should try:

.row {
  display: grid;
  grid-template-columns: auto auto auto auto;
  background: red;
  height: 3rem;
}

For 200px width on each cell, just add:

.cell {
    min-width: 200px;
    border: 1px solid black;
}
Dawntraoz
  • 26
  • 1
  • 2