提到布局许多人的感觉应该都是恐惧,为此许多人都背过一些很经典的布局计划,例如:圣杯布局双飞翼布局等十分耳熟的名词;

为了完成这些布局咱们有许多种完成计划,例如:table布局float布局定位布局等,当然现在比较盛行的肯定是flex布局

flex布局归于弹性布局,所谓弹性也能够了解为呼应式布局,而同为呼应式布局的还有Grid布局

Grid布局是一种二维布局,能够了解为flex布局的升级版,它的呈现让咱们在布局方面有了更多的挑选,废话不多说,下面开端全程高能;

本篇不会过多介绍grid的根底内容,更多的是一些布局的完成计划和一些小技巧;

常见布局

所谓的常见布局仅仅咱们在日常开发中经常会遇到的布局,例如:圣杯布局双飞翼布局这种名词我个人觉得不用太过于去在意;

由于这类布局最终的解释都会变成几行几列,内容在哪一行哪一列,而这些就十分直观的对标了grid的特性;

接下来咱们来一同看看一些十分常见的布局,并且用grid来完成;

1. 顶部 + 内容

学会Grid之后,我觉得再也没有我搞不定的布局了

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
        }
        body {
            display: grid;
            grid-template-rows: 60px 1fr;
            height: 100vh;
        }
        .header {
            background-color: #039BE5;
        }
        .content {
            background-color: #4FC3F7;
        }
        .header,
        .content {
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 24px;
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="content">Content</div>
</body>
</html>

学会Grid之后,我觉得再也没有我搞不定的布局了

2. 顶部 + 内容 + 底部

学会Grid之后,我觉得再也没有我搞不定的布局了

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
        }
        body {
            display: grid;
            grid-template-rows: 60px 1fr 60px;
            height: 100vh;
        }
        .header {
            background-color: #039BE5;
        }
        .content {
            background-color: #4FC3F7;
        }
        .footer {
            background-color: #039BE5;
        }
        .header,
        .content,
        .footer {
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 24px;
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="content">Content</div>
<div class="footer">Footer</div>
</body>
</html>

这儿示例和上面的示例唯一的区别便是多了一个footer,可是咱们能够看到代码并没有多少改变,这便是grid的强壮之处;

能够看码上的效果,这儿的内容区域是独自翻滚的,从而完成了headerfooter固定,内容区域翻滚的效果;

完成这个效果也十分简略,只需求在content上加上overflow: auto即可;

学会Grid之后,我觉得再也没有我搞不定的布局了

3. 左边 + 内容

学会Grid之后,我觉得再也没有我搞不定的布局了

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
        }
        body {
            display: grid;
            grid-template-columns: 240px 1fr;
            height: 100vh;
        }
        .left {
            background-color: #039BE5;
        }
        .content {
            background-color: #4FC3F7;
        }
        .left,
        .content {
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 24px;
        }
    </style>
</head>
<body>
<div class="left">Left</div>
<div class="content">Content</div>
</body>
</html>

这个示例效果其实和第一个是相似的,只不过是把grid-template-rows换成了grid-template-columns,这儿就不提供码上的示例了;

4. 顶部 + 左边 + 内容

学会Grid之后,我觉得再也没有我搞不定的布局了

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
        }
        body {
            display: grid;
            grid-template-rows: 60px 1fr;
            grid-template-columns: 240px 1fr;
            height: 100vh;
        }
        .header {
            grid-column: 1 / 3;
            background-color: #039BE5;
        }
        .left {
            background-color: #4FC3F7;
        }
        .content {
            background-color:  #99CCFF;
        }
        .header,
        .left,
        .content {
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 24px;
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="left">Left</div>
<div class="content">Content</div>
</body>
</html>

这个示例不同点在于header占据了两列,这儿咱们能够运用grid-column来完成,grid-column的值是start / end,例如:1 / 3表明从第一列到第三列;

假如确定这一列是占满整行的,那么咱们能够运用1 / -1来表明,这样假如后续变成顶部 + 左边 + 内容 + 右侧的布局,那么header就不需求修正了;

5. 顶部 + 左边 + 内容 + 底部

学会Grid之后,我觉得再也没有我搞不定的布局了

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
        }
        body {
            display: grid;
            grid-template-areas:
            "header header"
            "left content"
            "left footer";
            grid-template-rows: 60px 1fr 60px;
            grid-template-columns: 240px 1fr;
            height: 100vh;
        }
        .header {
            grid-area: header;
            background-color: #039BE5;
        }
        .left {
            grid-area: left;
            background-color: #4FC3F7;
        }
        .content {
            grid-area: content;
            background-color: #99CCFF;
        }
        .footer {
            grid-area: footer;
            background-color: #6699CC;
        }
        .header,
        .left,
        .content,
        .footer {
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 24px;
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="left">Left</div>
<div class="content">Content</div>
<div class="footer">Footer</div>
</body>
</html>

这个示例的小技巧是运用了grid-template-areas,运用这个特点能够让咱们经过代码来直观的看到布局的款式;

这儿的值是一个字符串,每一行代表一行,每个字符代表一列,例如:"header header"表明第一行的两列都是header,这儿的header是咱们自己界说的,能够是恣意值;

界说好了之后就能够在对应的元素上运用grid-area来指定对应的区域,这儿的值便是咱们在grid-template-areas中界说的值;

学会Grid之后,我觉得再也没有我搞不定的布局了

码上中的效果能够看到,左边的菜单和内容区域都是独自翻滚的,这儿的完成方法和第二个示例是相同的,只需求需求翻滚的元素上加上overflow: auto即可;

呼应式布局

呼应式布局指的是页面的布局会跟着屏幕的巨细而改变,这儿的改变能够是内容区域巨细能够主动调整,也能够是页面布局跟着屏幕巨细进行主动调整;

这儿我就用的页面来举例,这儿只提供一个思路,所以不会像上面那样提供那么多示例;

1. 根底布局完成

移动端布局

学会Grid之后,我觉得再也没有我搞不定的布局了

以移动端的效果开端,的移动端的布局便是上面的效果,这儿我简略的将页面分为了三个部分,分别是headernavigationcontent

注:这儿不是要100%复原的页面,仅仅为了演示grid布局,详细页面结构和最终完成的效果会有十分大的差异,这儿只会完成一些根底的布局;

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
        }
        body {
            display: grid;
            grid-template-areas:
            "header"
            "navigation"
            "content";
            grid-template-rows: 60px 48px 1fr;
            height: 100vh;
        }
        .header {
            grid-area: header;
            background-color: #039BE5;
        }
        .navigation {
            grid-area: navigation;
            background-color: #4FC3F7;
        }
        .content {
            grid-area: content;
            background-color: #99CCFF;
        }
        .header,
        .navigation,
        .content {
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 24px;
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="navigation">Navigation</div>
<div class="content">Content</div>
</body>
</html>

iPad布局

学会Grid之后,我觉得再也没有我搞不定的布局了

这儿是需求凭借媒体查询来完成的,在媒体查询中只需求调整一下grid-template-rowsgrid-template-columns的值即可;

由于这儿的效果是上面一个的延伸,为了阅览体会会移除上面相关的css代码,只保存需求修正的代码;

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        .right {
            display: none;
            background-color: #6699CC;
        }
        @media (min-width: 1000px) {
            body {
                grid-template-areas:
                  "header header"
                  "navigation navigation"
                  "content right";
                grid-template-columns: 1fr 260px;
            }
            .right {
                grid-area: right;
                display: flex;
                align-items: center;
                justify-content: center;
                font-size: 24px;
            }
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="navigation">Navigation</div>
<div class="content">Content</div>
<div class="right">Right</div>
</body>
</html>

PC端布局

学会Grid之后,我觉得再也没有我搞不定的布局了

和上面处理方法相同,由于Navigation移动到了左边,所以还要额定的修正一下grid-template-areas的值;

这儿就能够表现grid的强壮之处了,咱们能够简略的修正grid-template-areas就能够完成一个彻底不同的布局,并且代码量十分少;

为了居中显现内容,咱们需求在左右两侧加上一些空白区域,能够简略的运用.来完成,这儿的.表明一个空白区域;

由于内容的宽度基本上是固定的,所以留白区域简略的运用1fr进行占位即可,这样就能够平均的分配剩余的空间;

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        @media (min-width: 1220px) {
            body {
                grid-template-areas:
                  "header header header header header"
                  ". navigation content right .";
                grid-template-columns: 1fr 180px minmax(0, 720px) 260px 1fr;
                grid-template-rows: 60px 1fr;
            }
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="navigation">Navigation</div>
<div class="content">Content</div>
<div class="right">Right</div>
</body>
</html>

完善一些细节

学会Grid之后,我觉得再也没有我搞不定的布局了

最终的布局大约便是上图这样,这儿主要处理的各个版块的距离和呼应式内容区域的巨细,这儿的处理方法主要是运用column-gap和一个空的区域进行占位来完成的;

这儿的column-gap表明列与列之间的距离,值能够是pxemrem等基本的长度特点值,也能够运用核算函数,可是不能运用弹性值fr

空区域进行占位留距离其实我并不引荐,这儿仅仅演示grid布局能够完成的一些功用,详细的完成方法仍是要根据实际情况来定,这儿我更引荐运用margin来完成;

完好代码如下:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
        }
        body {
            display: grid;
            grid-template-areas:
            "header header header"
            "navigation navigation navigation"
            ". . ."
            ". content .";
            grid-template-columns: 1fr minmax(0, 720px) 1fr;
            grid-template-rows: 60px 48px 10px 1fr;
            column-gap: 10px;
            height: 100vh;
        }
        .header {
            grid-area: header;
            background-color: #039BE5;
        }
        .navigation {
            grid-area: navigation;
            background-color: #4FC3F7;
        }
        .content {
            grid-area: content;
            background-color: #99CCFF;
        }
        .right {
            display: none;
            background-color: #6699CC;
        }
        @media (min-width: 1000px) {
            body {
                grid-template-areas:
                  "header header header header"
                  "navigation navigation navigation navigation"
                  ". . . ."
                  ". content right .";
                grid-template-columns: 1fr minmax(0, 720px) 260px 1fr;
            }
            .right {
                grid-area: right;
                display: flex;
                align-items: center;
                justify-content: center;
                font-size: 24px;
            }
        }
        @media (min-width: 1220px) {
            body {
                grid-template-areas:
                  "header header header header header"
                  ". . . . ."
                  ". navigation content right .";
                grid-template-columns: 1fr 180px minmax(0, 720px) 260px 1fr;
                grid-template-rows: 60px 10px 1fr;
            }
        }
        .header,
        .navigation,
        .content {
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 24px;
        }
    </style>
</head>
<body>
<div class="header">Header</div>
<div class="navigation">Navigation</div>
<div class="content">Content</div>
<div class="right">Right</div>
</body>
</html>

简略复刻版

学会Grid之后,我觉得再也没有我搞不定的布局了

码上上的效果来说已经完成了大部分的布局和一些效果,目前来说便是还差一些交互,还有一些细节上的处理,感兴趣的同学能够自行完善;

异型布局

异性布局指的是页面中的元素不是依照常规的流式布局进行排版,又或者说不规则的布局,这儿我简略的列出几个布局,来看看grid是怎么完成的;

1. 照片墙

学会Grid之后,我觉得再也没有我搞不定的布局了

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style>
        html, body {
            margin: 0;
            padding: 0;
            background: #f2f3f5;
            overflow: auto;
        }
        body {
            display: grid;
            grid-template-columns: repeat(12, 100px);
            grid-auto-rows: 100px;
            place-content: center;
            gap: 6px;
            height: 100vh;
        }
        .photo-item {
            width: 200px;
            height: 200px;
            clip-path: polygon(50% 0, 100% 50%, 50% 100%, 0 50%);
        }
    </style>
</head>
<body>
</body>
<script>
    function randomColor() {
        return '#' + Math.random().toString(16).substr(-6);
    }
    let row = 1;
    let col = 1;
    for (let i = 0; i < 28; i++) {
        const div = document.createElement('div');
        div.className = 'photo-item';
        div.style.backgroundColor = randomColor();
        div.style.gridRow = `${row} / ${row + 2}`;
        div.style.gridColumn = `${col} / ${col + 2}`;
        document.body.appendChild(div);
        col += 2;
        if (col > 11) {
            row += 1;
            col = row % 2 === 0 ? 2 : 1;
        }
    }
</script>
</html>

这是一个十分简略的照片墙效果,假如不运用grid的话,咱们大约率是会运用定位去完成这个效果,可是换成grid的话就十分简略了;

并且代码量是十分少的,这儿就不提供码上的 demo 了,感兴趣的同学能够将代码复制下来自行检查效果;

2. 漫画效果

学会Grid之后,我觉得再也没有我搞不定的布局了

学会Grid之后,我觉得再也没有我搞不定的布局了

在漫画中有许多相似这种不规则的漫画框,假如运用定位的话,那么代码量会十分大,并且还需求核算一些方位,运用grid的话就十分简略了;

能够看到这儿还有一个气泡文字显现的效果,依照页面书写次序,气泡是不会显现的,这儿咱们能够运用z-index来完成,这儿的z-index值越大,元素就越靠前;

并且气泡文字效果也是经过grid来进行排版的,并没有运用其他的布局来完成,代码量也并不多,感兴趣的同学能够自行检查;

3. 画报效果

学会Grid之后,我觉得再也没有我搞不定的布局了

学会Grid之后,我觉得再也没有我搞不定的布局了

在一个画报中,咱们经常会看到文字和图片混合排版的效果,由于这儿直接运用的是渐变的布景,并且我的文字都是随意进行摆放的,没有什么规律,所以看起来会比较紊乱;

在画报效果中看似文字排版十分紊乱不规则,可是实际上规划师在规划的时分也是会划分区域的,当然用定位也是没问题的,可是运用grid的话就会简略许多;

我这儿将页面划分为12 * 12区域的网格,然后顺次对不同的元素进行独自摆放和款式的设置;

流式布局

流式布局指的是页面的内容会跟着屏幕的巨细而改变,流式布局也能够了解为呼应式布局;

可是不同于呼应式布局的是,流式布局的布局不会像呼应式布局那样发生改变,仅仅内容会跟着轴进行活动;

通常这种指的是grid-template-columns: repeat(auto-fit, minmax(0, 1fr))这种;

直接看效果:

学会Grid之后,我觉得再也没有我搞不定的布局了

这儿有两个关键字,一个是auto-fit,还有一个是auto-fill,在行为上它们是相同的,不同的是它们在网格创立的不同,

学会Grid之后,我觉得再也没有我搞不定的布局了

就像上面图中看到的相同,运用auto-fit会将空的网格进行折叠,能够看到他们的完毕colum的数字都是6;

像咱们上面的实例中不会呈现这个问题,由于咱们运用了呼应式单位fr,只要运用固定单位才会呈现这个现象;

感兴趣的同学能够将minmax(200px, 1fr)换成200px测验;

比照 Flex 布局

在我上面介绍了这么多的布局场景和事例,其实能够很明显的发现一件事,那便是我运用grid进行的布局基本上都是大结构;

当然上面也有一些布局运用flex也是能够完成的,可是咱们再换个思路,除了flex能够做到上面的一些布局,float布局、table布局、定位布局其实也都能完成;

不同的是float布局、table布局、定位布局基本上都是一些hack的计划,就拿table布局来说,table本身便是一个html标签,效果便是用来制作表格,被拿来作为布局的一种计划也是迫不得已;

web布局发展到现在的咱们有了正儿八经能够布局的计划flex,为什么又要出一个grid呢?

grid的呈现肯定不是用来替代flex的,在我上面的完成的一些布局事例中,也能够看到我还会运用flex

我个人了解的是运用grid进行主体的大结构的搭建,flex作为一些小组件的布局控制,两者调配运用;

flex能完成一些grid欠好完成的布局,相同grid也能够完成flex完成困难的布局;

本身它们的定位就不痛,flex作为一维布局的首选,grid定位便是比flex高一个维度,它的定位是二维布局,所以他们之间没有必要进行比照,合理运用就好;

总结

上面介绍的这么多根据grid布局完成的布局计划,足以看出grid布局的强壮;

grid布局的体系十分庞大,本文仅仅梳理出一些常见的布局场景,经过grid布局去完成这些布局,来体会grid带来的便当;

可能需求彻底了解我上面的悉数示例需求对grid有一定的了解才能够,可是都看到这儿了,不妨去深挖一下;

grid布局作为一项强壮的布局技能,有望在未来继续发展,除了我上面提到的布局,grid还有许多小技巧来完成十分多的布局场景;

碍于我的见识和文笔的约束,我这次介绍grid肯定是有许多缺乏的,可是仍是期望这篇文章能为你关于布局相关能有新的认识;