CSS 即使有前缀,网格布局在 IE11 中也不起作用

CSS Grid Layout not working in IE11 even with prefixes

我正在为我的网格使用以下 HTML 标记。

<section class="grid">
    <article class="grid-item width-2x height-2x">....</article>
    <article class="grid-item">....</article>
    <article class="grid-item">....</article>
    <article class="grid-item width-2x">....</article>
    <article class="grid-item height-2x">....</article>
    <article class="grid-item">....</article>
    <article class="grid-item">....</article>
    <article class="grid-item width-2x height-2x">....</article>
</section>

SCSS 代码如下所示:

.grid {
    display: grid;
    grid-template-columns: repeat( 4, 1fr );
    grid-gap: 30px;
    align-items: start;

    .grid-item {
        &.height-2x {
            grid-row: span 2;
        }
        &.width-2x {
            grid-column: span 2;
        }
    }
}

由于我在我的工作流程中使用了自动前缀器,它会自动添加带有 -ms 前缀的所有相关属性。我可以通过 inspect element 来确认。

现在,问题是此代码在 Chrome、Firefox 和 Opera 中运行良好,但当我在 Microsoft Edge 或 IE 11 中打开此页面时,所有网格项目在第一个单元格中相互重叠。根据 this site,这些浏览器支持带有 -ms 前缀的 CSS 网格布局。我已经为这个场景创建了一个 CodePen。

CodePen Link

为什么它不起作用?

.grid {
  display: -ms-grid;
  display: grid;
  -ms-grid-columns: (1fr)[4];
  grid-template-columns: repeat(4, 1fr);
  -ms-grid-rows: (270px)[4];
  grid-template-rows: repeat(4, 270px);
  grid-gap: 30px;
}

.grid .grid-item {
  background-color: #000;
  color: #fff;
  text-align: center;
  line-height: 270px;
}

.grid .grid-item.height-2x {
  -ms-grid-row: span 2;
  grid-row: span 2;
}

.grid .grid-item.width-2x {
  -ms-grid-column: span 2;
  grid-column: span 2;
}
<section class="grid">
  <article class="grid-item width-2x height-2x">....</article>
  <article class="grid-item">....</article>
  <article class="grid-item">....</article>
  <article class="grid-item width-2x">....</article>
  <article class="grid-item height-2x">....</article>
  <article class="grid-item">....</article>
  <article class="grid-item">....</article>
  <article class="grid-item width-2x height-2x">....</article>
</section>

IE11 使用 older version of the Grid specification.

您正在使用的属性在旧的网格规范中不存在。使用前缀没有区别。

这是我立即看到的三个问题。


repeat()

repeat() 函数在旧规范中不存在,因此 IE11 不支持它。

您需要使用 中介绍的正确语法,或者声明所有行和列的长度。

而不是:

.grid {
  display: -ms-grid;
  display: grid;
  -ms-grid-columns: repeat( 4, 1fr );
      grid-template-columns: repeat( 4, 1fr );
  -ms-grid-rows: repeat( 4, 270px );
      grid-template-rows: repeat( 4, 270px );
  grid-gap: 30px;
}

使用:

.grid {
  display: -ms-grid;
  display: grid;
  -ms-grid-columns: 1fr 1fr 1fr 1fr;             /* adjusted */
      grid-template-columns:  repeat( 4, 1fr );
  -ms-grid-rows: 270px 270px 270px 270px;        /* adjusted */
      grid-template-rows: repeat( 4, 270px );
  grid-gap: 30px;
}

旧规范参考: https://www.w3.org/TR/2011/WD-css3-grid-layout-20110407/#grid-repeating-columns-and-rows


span

旧规范中不存在 span 关键字,因此 IE11 不支持它。您必须为这些浏览器使用等效的属性。

而不是:

.grid .grid-item.height-2x {
  -ms-grid-row: span 2;
      grid-row: span 2;
}
.grid .grid-item.width-2x {
  -ms-grid-column: span 2;
      grid-column: span 2;
}

使用:

.grid .grid-item.height-2x {
  -ms-grid-row-span: 2;          /* adjusted */
      grid-row: span 2;
}
.grid .grid-item.width-2x {
  -ms-grid-column-span: 2;       /* adjusted */
      grid-column: span 2;
}

旧规范参考: https://www.w3.org/TR/2011/WD-css3-grid-layout-20110407/#grid-row-span-and-grid-column-span


grid-gap

grid-gap 属性 以及它的简写形式 grid-column-gapgrid-row-gap 在旧规范中不存在,所以它们' IE11 不支持。你必须找到另一种方法来分开盒子。我还没有阅读整个旧规范,所以可能有一种方法。否则,尝试边距。


网格项目自动放置

有一些 discussion in the old spec about grid item auto placement,但该功能从未在 IE11 中实现。 (自动放置网格项目现在是当前浏览器的标准配置)。

因此,除非您专门定义网格项目的位置,否则它们将堆叠在单元格 1,1 中。

使用 -ms-grid-row-ms-grid-column 属性。

Faisal Khurshid 和 Michael_B 已经给出了答案。
这只是试图使可能的解决方案更加明显。

对于 IE11 及以下版本,您需要在 parent div 中启用网格的旧规范,例如body 或像这里 "grid" 像这样:

.grid-parent{display:-ms-grid;}

然后定义列和行的数量和宽度,例如所以:

.grid-parent{
  -ms-grid-columns: 1fr 3fr;
  -ms-grid-rows: 4fr;
}

最后你需要明确地告诉浏览器你的元素(项目)应该放在什么地方,例如像这样:

.grid-item-1{
  -ms-grid-column: 1;
  -ms-grid-row: 1;
}

.grid-item-2{
  -ms-grid-column: 2;
  -ms-grid-row: 1;
}

Michael 给出了一个非常全面的答案,但我想指出一些您仍然可以做的事情,以便能够以几乎无痛的方式在 IE 中使用网格。

支持 repeat 功能

您仍然可以使用重复功能,它只是隐藏在不同的语法后面。而不是写repeat(4, 1fr),你必须写(1fr)[4]。而已。 目前情况见本系列文章:https://css-tricks.com/css-grid-in-ie-debunking-common-ie-grid-misconceptions/

支持网格间隙

除 IE 之外的所有浏览器都支持网格间距。因此,您可以使用 @supports 规则为所有新浏览器有条件地设置网格间隙:

示例:

.grid {
  display: grid;
}
.item {
  margin-right: 1rem;
  margin-bottom: 1rem;
}
@supports (grid-gap: 1rem) {
  .grid {
    grid-gap: 1rem;
  }
  .item {
    margin-right: 0;
    margin-bottom: 0;
  }
}

有点冗长,但从好的方面来说,您不必为了支持 IE 而完全放弃网格。

使用自动前缀

我怎么强调都不为过 - 只需在构建步骤中使用 autoprefixer 即可解决网格问题的一半。以符合标准的方式编写 CSS,然后让 autoprefixer 自动转换所有旧规范属性。当您决定不想支持 IE 时,只需更改浏览器列表配置中的一行,您就会从构建的文件中删除所有特定于 IE 的代码。

为了支持 IE11 的自动放置,我每次在 1 维 中使用网格布局时,都会将 grid 布局转换为 table 布局。我还使用 margin 而不是 grid-gap

结果是一样的,看这里怎么做https://jsfiddle.net/hp95z6v1/3/