【问题标题】:Filling empty cells in CSS Grid Layout填充 CSS 网格布局中的空单元格
【发布时间】:2017-12-14 10:53:58
【问题描述】:

我有一组通过 CSS 网格布局尽可能“自动”排列的 div 磁贴;我的最终想法是,即使我不知道有多少瓷砖,它们的大小和位置都会正确。这工作正常。

现在,我希望将任何被点击的图块的面积加倍。据我所知,这意味着增加此图块的跨度:

grid-row: span 2;
grid-column: span 2;

如果我单击不在最右侧列中的任何图块,我对结果感到满意。当最右边的图块展开时,它们会被包裹到下一行。

有没有什么办法可以强制这些瓦片向左展开,让其他非活动瓦片被包裹起来?

Codepen 示例here

$('div.tile').click(function() {
  $('div.tile').not(this).removeClass('chosen');
  $(this).toggleClass('chosen');
  
  /*
Attempt to find current placement, to see if we could change the span rules based on results. Probably disregard.
  */
  var colCount = $('div.wrapper').css('grid-template-columns').split(' ').length;
  console.log(colCount);
  
  var placement = $(this).css('grid-row');
  console.log(placement);
});
body {
  margin: 0;
  padding: 0;
  background-color: #eee;
}

.wrapper {
  display: grid;
  margin: 18px;
  
  grid-template-columns: repeat(auto-fill, minmax(252px, 1fr));
  grid-auto-rows: 286px;
  grid-gap: 18px;
}

.tile {
  position: relative;
  background-color: #eee;
  background-color: #149;
  
  text-align: center;
  box-shadow:
    0 3px 12px rgba(0,0,0, 0.15),
    0 4px 6px rgba(0,0,0, 0.25);
}
.tile.chosen {
  grid-row: span 2;
  grid-column: span 2;
}
.tile.chosen::before {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  content: " ";
  background-color: rgba(255,255,255,.2);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="wrapper">
  <div class="tile">A</div>
  <div class="tile">B</div>
  <div class="tile">C</div>
  <div class="tile">D</div>
  <div class="tile">E</div>
  <div class="tile">F</div>
  <div class="tile">G</div>
  <div class="tile">H</div>
  <div class="tile">I</div>
</div>

【问题讨论】:

  • 我最终选择了 Michael 下面提到的 Javascript (jQuery) 路线。如果有人偶然发现这个问题,我的 codepen 链接会更新。

标签: javascript jquery css css-grid


【解决方案1】:

使用 CSS 网格自动放置

CSS grid-auto-flow 属性控制自动放置的网格项在网格中的放置方式。

这个属性有三个可能的值:

  • row(默认)
  • column
  • dense

使用dense,自动放置算法会用适合的项目填充未占用的单元格。

这是您的代码,网格容器上带有 grid-auto-flow: dense

$('div.tile').click(function() {
  $('div.tile').not(this).removeClass('chosen');
  $(this).toggleClass('chosen');
  var colCount = $('div.wrapper').css('grid-template-columns').split(' ').length;
  console.log(colCount);
  var placement = $(this).css('grid-row');
  console.log(placement);
});
body {
  margin: 0;
  padding: 0;
  background-color: #eee;
}

.wrapper {
  display: grid;
  margin: 18px;
  grid-template-columns: repeat(auto-fill, minmax(252px, 1fr));
  grid-auto-rows: 286px;
  grid-gap: 18px;
  grid-auto-flow: dense; /* NEW */
}

.tile {
  position: relative;
  background-color: #eee;
  background-color: #149;
  text-align: center;
  box-shadow: 0 3px 12px rgba(0, 0, 0, 0.15), 0 4px 6px rgba(0, 0, 0, 0.25);
}

.tile.chosen {
  grid-row: span 2;
  grid-column: span 2;
}

.tile.chosen::before {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  content: " ";
  background-color: rgba(255, 255, 255, .2);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="wrapper">
  <div class="tile">A</div>
  <div class="tile">B</div>
  <div class="tile">C</div>
  <div class="tile">D</div>
  <div class="tile">E</div>
  <div class="tile">F</div>
  <div class="tile">G</div>
  <div class="tile">H</div>
  <div class="tile">I</div>
</div>

revised codepen


来自规范:

7.7. Automatic Placement: the grid-auto-flow property

未明确放置的网格项目会自动放置到 网格容器中自动放置的未占用空间 算法。

grid-auto-flow 控制自动放置算法的工作方式, 准确指定自动放置的项目如何流入网格。

row

自动放置算法通过依次填充每一行来放置项目,并根据需要添加新行。如果既没有提供row 也没有提供column,则假定为row

column

自动放置算法通过依次填充每一列来放置项目,并根据需要添加新列。

dense

如果指定,自动放置算法使用“密集”包装 算法,它会尝试在网格中较早地填充孔 较小的项目稍后出现。这可能会导致项目出现 乱序,这样做会填补较大项目留下的漏洞。


使用 CSS 网格定义放置

CSS Grid 规范提供了许多用于调整和定位网格项的属性和方法。因此,如果您不必依赖自动放置,请使用定义的放置以获得更多控制。

grid-container {
  display: grid;
  grid-template-rows: repeat(4, 25%);
  grid-template-columns: repeat(4, 25%);
  grid-gap: 5px;
  width: 400px;
  height: 400px;
}

[left]:hover {
  grid-column: -1 / -3;
  grid-row: 1 / 2;
  background-color: orange
}

[right]:hover {
  grid-column: 1 / 3;
  grid-row: 2 / 3;
  background-color: orange
}

[down]:hover {
  grid-column: -1 / -2;
  grid-row: 2 / 4;
  background-color: orange
}

[up]:hover {
  grid-column: 3 / 4;
  grid-row: -4 / -2;
  background-color: orange
}

grid-item {
  background-color: lightgreen;
  display: flex;
  align-items: center;
  justify-content: center;
  text-align: center;
}
<grid-container>
  <grid-item></grid-item>
  <grid-item></grid-item>
  <grid-item></grid-item>
  <grid-item left>HOVER<br>to go left</grid-item>
  <grid-item right>HOVER<br>to go right</grid-item>
  <grid-item></grid-item>
  <grid-item></grid-item>
  <grid-item down>HOVER<br>to go down</grid-item>
  <grid-item></grid-item>
  <grid-item></grid-item>
  <grid-item up>HOVER<br>to go up</grid-item>
  <grid-item></grid-item>
</grid-container>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-30
    • 1970-01-01
    • 2021-05-19
    • 2015-06-04
    • 1970-01-01
    相关资源
    最近更新 更多