【问题标题】:How to create a grid system based on flexbox?如何基于flexbox创建网格系统?
【发布时间】:2019-07-03 05:25:53
【问题描述】:

出于学习的目的,我尝试创建一个基于flexbox的网格系统,但是用它创建东西后发现了一些问题:当总列占用100%的空间时,最后一列进入下一行(容器为flex-flow: row wrap;) 但是当它们不是 100% 时(例如,一列占 30%,另一列占 65%)它们在同一行...然后我发现这与边距有关,但仍然我解决不了。

我现在的疑问是:列的宽度使用什么?弹性基础?宽度

如何解决要解决的边距问题?我在 github 项目中看到过一个使用“gap”之类的东西,但我仍然不太明白它是如何工作的......

我尝试将 calc() 属性与 10px 的“- $ gap”一起添加,但我仍然无法按照应有的方式生成网格。

我之前的代码是这样的:

.row {
    display: flex;
}

@for $i from 1 through $grid-cols {

    @media (max-width: 768px) {
        .col-mob-#{$i} {
            width: 100 / ($grid-cols / $i) * 1%;
        }
    }

    @media (min-width: 769px) and (max-width: 1023px) {
        .col-tab-#{$i} {
            width: 100 / ($grid-cols / $i) * 1%;
        }
    }

    @media (min-width: 1024px) and (max-width: 1407px) {
        .col-hd-#{$i} {
            width: 100 / ($grid-cols / $i) * 1%;
        }
    }

    @media (min-width: 1408px) {
        .col-fhd-#{$i} {
            width: 100 / ($grid-cols / $i) * 1%;
        }
    }
}

编辑:我设法按照我想要的方式保留了它:

$grid-cols: 12;
$gap: 0.75rem !default;

// .row is used as container for divs with columns
.row {
    display: flex;
}

@for $i from 1 through $grid-cols {

    @media (max-width: 768px) {
        .col-mob-#{$i} {
            flex-basis: calc((100 / (#{$grid-cols} / #{$i}) * 1%) - #{$gap});
        }
    }
    // ....

【问题讨论】:

    标签: css sass flexbox


    【解决方案1】:

    FLexbox 是线性的,而 Grid 是二维的。有很多方法可以解决这个问题。但你需要使用flex-wrap: no-wrap

    我会先定义一个弹性行。

    .outerRow {
        display: 'flex';
        # Do not allow wrap (event though this is default)
        flex-wrap: 'no-wrap';
        # Fill the full height
        align-items: 'stretch';
    }
    

    现在你的专栏。如果您想要两列 25% 和一列 50%,请执行以下操作:

    .quarter {
        flex-grow: 1;
    }
    .half {
        flex-grow: 2;
    }
    

    注意它们是比率。

    那么你需要制作列类:

    .column {
        display: 'flex';
        # Make this a flex-column
        flex-direction: 'column';
        # Do not allow wrap (event though this is default)
        flex-wrap: 'no-wrap';
        # Fill the full width
        align-items: 'stretch';
    }
    

    然后在这些列中,您可以进行线性弹性排列。您可以使用上面的 quarterColumn 或 halfColumn 类......或者您可以像这样编辑类:

    .column {
        display: 'flex';
        flex-direction: 'column';
        flex-wrap: 'no-wrap';
        # Everything floats to flex-start (event though this is default)
        justify-content: 'flex-start';
    }
    

    用块级元素填充列,最终得到一个 pinterest 风格的交错网格。

    <div class="outerRow">
        <div class="quarter column">
            <div></div>
            <div></div>
            <div></div>
        </div>
        <div class="half column">
            <div></div>
            <div></div>
            <div></div>
        </div>
        <div class="quarter column">
            <div></div>
            <div></div>
            <div></div>
        </div>
    </div>
    

    或者如果你想让它们统一:

    <div class="outerRow">
        <div class="quarter column">
            <div class="half"></div>
            <div class="half"></div>
            <div class="half"></div>
        </div>
        <div class="half column">
            <div class="half"></div>
            <div class="half"></div>
            <div class="half"></div>
        </div>
        <div class="quarter column">
            <div class="half"></div>
            <div class="half"></div>
            <div class="half"></div>
        </div>
    </div>
    

    记住 flex-grow 值是相互之间的比率

    阅读https://css-tricks.com/snippets/css/a-guide-to-flexbox/

    :)

    【讨论】:

    • 好吧,使用 flex-grow 我不会有边距问题,或者会吗?我进行了编辑并设法使用 calc() 解决了问题,我认为它没有被 sass “编译”,但实际上它带有足够的代码并且浏览器可以完成工作,所以我可以添加一些边距+ 如果我愿意,可以在两者之间使用空格。别名,我将使用 flex-grow 进行测试,看看它是如何工作的。
    • 我认为你应该停止使用媒体查询并停止使用 calc。使用弹性属性flex-growflex--shrinkflex-basis
    • 如果我想要一个仅在智能手机中具有 100% 空间的列,并且在分辨率为 1280x720 的显示器上具有 30% 的空间,我该怎么办?无论如何,我似乎应该使用媒体查询
    • flex-basis: 320px; flex-shrink: 0; flex-grow: 1; max-width: 430px;... 类似的东西?
    • flex-basis: 430px; flex-shrink: 1; flex-grow: 0;
    【解决方案2】:

    您可以使用添加为边距的间隙值简单地减小宽度。诀窍是考虑间隙仅在内部,因此您需要使用-1 来正确计算宽度:

    .row {
        display: flex;
    }
    
    $grid-cols : 8;
    $gaps : 10px;
    
    .row > div:not(:last-child) {
      margin-right: $gaps;
    }
    
    @for $i from 1 through $grid-cols {
    
        @media (max-width: 768px) {
            .col-mob-#{$i} {
                width: (calc((100% - (#{$grid-cols / $i} - 1)*#{$gaps})/ #{($grid-cols / $i)}));
            }
        }
    
        @media (min-width: 769px) and (max-width: 1023px) {
            .col-tab-#{$i} {
                width: (calc((100% - (#{$grid-cols / $i} - 1)*#{$gaps})/ #{($grid-cols / $i)}));
            }
        }
    
        @media (min-width: 1024px) and (max-width: 1407px) {
            .col-hd-#{$i} {
                width: (calc((100% - (#{$grid-cols / $i} - 1)*#{$gaps})/ #{($grid-cols / $i)}));
            }
        }
    
        @media (min-width: 1408px) {
            .col-fhd-#{$i} {
                width: (calc((100% - (#{$grid-cols / $i} - 1)*#{$gaps})/ #{($grid-cols / $i)}));
            }
        }
    }
    

    完整代码编译:

    .row {
      display: flex;
      flex-wrap:wrap;
      margin:5px;
    }
    .row > div{
      height:50px;
      background:red;
    }
    
    .row > div:not(:last-child) {
      margin-right: 10px;
    }
    
    @media (max-width: 768px) {
      .col-mob-1 {
        width: calc((100% - (8 - 1)*10px)/ 8);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-1 {
        width: calc((100% - (8 - 1)*10px)/ 8);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-1 {
        width: calc((100% - (8 - 1)*10px)/ 8);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-1 {
        width: calc((100% - (8 - 1)*10px)/ 8);
      }
    }
    @media (max-width: 768px) {
      .col-mob-2 {
        width: calc((100% - (4 - 1)*10px)/ 4);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-2 {
        width: calc((100% - (4 - 1)*10px)/ 4);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-2 {
        width: calc((100% - (4 - 1)*10px)/ 4);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-2 {
        width: calc((100% - (4 - 1)*10px)/ 4);
      }
    }
    @media (max-width: 768px) {
      .col-mob-3 {
        width: calc((100% - (2.6666666667 - 1)*10px)/ 2.6666666667);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-3 {
        width: calc((100% - (2.6666666667 - 1)*10px)/ 2.6666666667);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-3 {
        width: calc((100% - (2.6666666667 - 1)*10px)/ 2.6666666667);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-3 {
        width: calc((100% - (2.6666666667 - 1)*10px)/ 2.6666666667);
      }
    }
    @media (max-width: 768px) {
      .col-mob-4 {
        width: calc((100% - (2 - 1)*10px)/ 2);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-4 {
        width: calc((100% - (2 - 1)*10px)/ 2);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-4 {
        width: calc((100% - (2 - 1)*10px)/ 2);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-4 {
        width: calc((100% - (2 - 1)*10px)/ 2);
      }
    }
    @media (max-width: 768px) {
      .col-mob-5 {
        width: calc((100% - (1.6 - 1)*10px)/ 1.6);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-5 {
        width: calc((100% - (1.6 - 1)*10px)/ 1.6);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-5 {
        width: calc((100% - (1.6 - 1)*10px)/ 1.6);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-5 {
        width: calc((100% - (1.6 - 1)*10px)/ 1.6);
      }
    }
    @media (max-width: 768px) {
      .col-mob-6 {
        width: calc((100% - (1.3333333333 - 1)*10px)/ 1.3333333333);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-6 {
        width: calc((100% - (1.3333333333 - 1)*10px)/ 1.3333333333);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-6 {
        width: calc((100% - (1.3333333333 - 1)*10px)/ 1.3333333333);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-6 {
        width: calc((100% - (1.3333333333 - 1)*10px)/ 1.3333333333);
      }
    }
    @media (max-width: 768px) {
      .col-mob-7 {
        width: calc((100% - (1.1428571429 - 1)*10px)/ 1.1428571429);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-7 {
        width: calc((100% - (1.1428571429 - 1)*10px)/ 1.1428571429);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-7 {
        width: calc((100% - (1.1428571429 - 1)*10px)/ 1.1428571429);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-7 {
        width: calc((100% - (1.1428571429 - 1)*10px)/ 1.1428571429);
      }
    }
    @media (max-width: 768px) {
      .col-mob-8 {
        width: calc((100% - (1 - 1)*10px)/ 1);
      }
    }
    @media (min-width: 769px) and (max-width: 1023px) {
      .col-tab-8 {
        width: calc((100% - (1 - 1)*10px)/ 1);
      }
    }
    @media (min-width: 1024px) and (max-width: 1407px) {
      .col-hd-8 {
        width: calc((100% - (1 - 1)*10px)/ 1);
      }
    }
    @media (min-width: 1408px) {
      .col-fhd-8 {
        width: calc((100% - (1 - 1)*10px)/ 1);
      }
    }
    <div class="row">
      <div class="col-mob-3">
      </div>
      <div class="col-mob-5">
      </div>
    </div>
    <div class="row">
      <div class="col-mob-1">
      </div>
      <div class="col-mob-1">
      </div>
      <div class="col-mob-1">
      </div>
      <div class="col-mob-1">
      </div>
      <div class="col-mob-1">
      </div>
      <div class="col-mob-1">
      </div>
      <div class="col-mob-1">
      </div>
      <div class="col-mob-1">
      </div>
    </div>
    <div class="row">
      <div class="col-mob-4">
      </div>
      <div class="col-mob-4">
      </div>
    </div>
    <div class="row">
      <div class="col-mob-2">
      </div>
      <div class="col-mob-6">
      </div>
    </div>

    【讨论】:

      猜你喜欢
      • 2015-04-09
      • 1970-01-01
      • 2012-11-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-12-03
      相关资源
      最近更新 更多