css布局方式_网页布局都有哪种?一般都用什么布局?

e2cf850d041543ce79ff88bbb36a9ef6.gif随着Web技术不断的革新,CSS近几年也变得多年前要更强大。在Web开发中,CSS是不可或缺的一部分,对于很多Web开发者来说,有很多CSS属性不知道,或者说他们知道,但忘记在最恰当的时候使用最适合的CSS属性。而且时至今日,其中有一些CSS的属性可以让开发者能节约更多的时间。比如说,在Web布局中,现代CSS特性就可以更好的帮助我们快速实现,例如等高布局,水平垂直居中,经典的圣杯布局、宽高比例、页脚保持在底部等。在本文中,我将会介绍一些不同的CSS属性来实现这些效果,希望大家会感兴趣。更希望对大家今后的工作有所帮助。水平垂直居中

如何实现水平垂直居中 可以说是CSS面试题中的经典面试题,在多年前这个面试题给很多同学都带来了困惑,但 Flexbxo布局模块 和 CSS Grid布局模块 的到来,可以说实现水平垂直居中已是非常的容易。

▐  Flexbox中实现水平垂直居中

在Flexbox布局模块中,不管是单行还是多行,要让它们在容器中水平垂直居中都是件易事,而且方法也有多种。最常见的是在Flex容器上设置对齐方式,在Flex项目上设置margin:auto

先来看在Flex容器上设置对齐方式。

Flex容器和Flex项目上设置对齐方式

你可能已经知道在Flex容器上设置justify-contentalign-items的值为center时,可以让元素在Flex容器中达到水平垂直居中的效果。来看一个示例:

/* CSS */.flex__container {    display: flex;    justify-content: center;    align-items: center;}

效果如下:

77ed94d34488436a8934aa61b2f832b2.png

Demo(https://codepen.io/airen/embed/YzwYRRy)

这种方式特别适应于让Icon图标在容器中水平垂直居中,不同的是在Icon图标容器上显示设置display: inline-flex。比如下面这个示例:

/* CSS */.flex__container {    display: inline-flex;    align-items: center;    justify-content: center;}

效果如下:

86a65376b5b0efcd439572bfc6512f40.png

Demo(https://codepen.io/airen/embed/xxZpQNv)

在这种模式之下,如果要让多个元素实现水平垂直居中的效果,那还需要加上flex-direction: column,比如:

:)
/* CSS */.flex__container { display: flex; flex-direction: column; justify-content: center; align-items: center;}

效果如下:

cb360f3c8e19ebb9a877911474521607.png

Demo(https://codepen.io/airen/embed/QWyazpZ)

在Flexbox布局中,还可以像下面这样让Flex项目在Flex容器中达到水平垂直居中的效果:

/* CSS */.flex__container {    display: flex; // 或inline-flex    justify-content: center;}.flex__item {    align-self: center;}

效果如下:

d53f8254a165eed7237cd330f174653f.png

Demo(https://codepen.io/airen/embed/yLepGKW)

如果在Flex容器中有多个Flex项目时,该方法同样有效:

.flex__container {    display: flex; // 或inline-flex    justify-content: center;}.flex__container > * {    align-self: center;}

比如下面这个效果:

808ace435df30c7b7b116c42dd594e04.png

Demo(https://codepen.io/airen/embed/bGEaOjm)

除此之外,还可以使用place-content: center让Flex项目实现水平垂直居中:

.flex__container {    display: flex;    place-content: center;}.flex__item {    align-self: center;}

效果如下:

6a5e6f9b6bd3d4d630dbaaa25038fd1c.png

Demo(https://codepen.io/airen/embed/gOPoZQz)

或者换:

.flex__container {    display: flex;    place-content: center;    place-items: center;}

效果如下:

ee27dc671afe9658d7c2f4809bb2dd80.png

Demo(https://codepen.io/airen/embed/JjGMwzE)

这两种方式同样适用于Flex容器中有多个Flex项目的情景:

.flex__container {    display: flex;    flex-direction: column;    place-content: center;}.flex__container > * {    align-self: center;}// 或.flex__container {    display: flex;    flex-direction: column;    place-content: center;    place-items: center;}

效果如下:

8e4658389932fd08b9f107ff5922ae17.png

Demo(https://codepen.io/airen/embed/XWXVoLd)

可能很多同学对于place-contentplace-items会感到陌生。其实place-contentalign-contentjustify-content的简写属性;而place-itemsalign-itemsjustify-items的简写属性。即:

.flex__container {    place-content: center;    place-items: center;}

等效于:

.flex__container {    align-content: center;    justify-content: center;    align-items: center;    justify-items: center;}

虽然扩展出来有四个属性,但最终等效于:

.flex__container {    display: flex;    align-items: center;    justify-content: center;}// 多行.flex__container {    display: flex;    flex-direction: column;    align-items: center;    justify-content: center;}

在Flex项目上设置`margin: auto`

如果在Flex容器中只有一个Flex项目,还可以显式在Flex项目中显式设置margin的值为auto,这样也可以让Flex项目在Flex容器中水平垂直居中。例如:

.flex__container {    display: flex; // 或 inline-flex}.flex__item {    margin: auto;}

效果如下:

b993bcc990e269a82489c70971152cf6.png

Demo(https://codepen.io/airen/embed/KKVZJNp)

整个过程,你可以通过下面这个示例来体验。尝试着选中不同方向的margin值:

12a0e8664ebfb7ef79fc9b08eb82f0d2.gif

Demo(https://codepen.io/airen/embed/gOPoqRq

▐  Grid中实现水平垂直居中

CSS Grid布局可以说是现代Web布局中的银弹。它也是到目前为止布局系统中唯一一个二维布局系统。

在CSS Grid布局中,只需要仅仅的几行代码也可以快速的帮助我们实现水平垂直居中的效果。比如下面这个示例:

/* CSS */.grid {    display: grid; // 或 inline-grid    place-items: center}

效果如下:

5a9f8f3624f6d8f456aec848cbf5bcf7.png

Demo(https://codepen.io/airen/embed/zYrRYxW)

在CSS Grid布局模块中,只要显式设置了display: grid(或inline-grid)就会创建Grid容器和Grid项目,也会自动生成网格线,即行和列(默认为一行一列)。

46e1446063e9ff64468a3ef691f87db8.png

在没有显式地在Grid容器上设置grid-template-columnsgrid-template-rows,浏览器会将Grid容器默认设置为Grid内容大小:

51892669db5d4e4ba93c649a81bc5e7e.png

这种方法也适用于CSS Grid容器中有多个子元素(Grid项目),比如:

:)

这个时候你看到的效果如下:

61bd765ab1e6d6480d3e7167c81d8402.png

Demo(https://codepen.io/airen/embed/PoZQoGP)

而且palce-items适用于每个单元格。这意味着它将居中单元格的内容。比如下面这个示例:

Special title treatment

With supporting text below as a natural lead-in to additional content.

Go somewhere
/* CSS */.grid__container { display: grid; place-items: center; grid-template-columns: repeat(2, 1fr); gap: 2vh;}.grid__item { display: grid; place-items: center;}

效果如下:

95be751e4a14cc094ac778df04fc846c.png

Demo(https://codepen.io/airen/embed/mdVXdpe)

等高布局


等高布局也是Web中非常常见的一种布局方式,而且实现等高布局的方案也有很多种。这里我们主要来看Flexbox布局模块和Grid布局模块给我们带来了什么样的变化。

在Flexbox和Grid布局模块中,让我们实现等高布局已经是非常的简单了,比如:

            /* CSS */.flex__container {    display: flex; // 或 inline-flex}

简单地说,在容器上显式设置了display的值为flexinline-flex,该容器的所有子元素的高度都相等,因为容器的align-items的默认值为stretch

这个时候你看到的效果如下:

ea6c034bd86d174420ee288f0afbe19b.png

Demo(https://codepen.io/airen/embed/NWxyOQq)

这种方式特别适用于卡片组件中:

5d1d050ac05d8e052b54a8f38f95a160.png

Demo(https://codepen.io/airen/embed/OJMQoOO)

在Grid布局模块中类似:

            /* CSS */.grid__container {    display: grid;    grid-template-columns: 20vw 1fr 20vw; /* 根据需求调整值*/}

效果如下:

2b7dc84b68b95329d836e083c803377e.png

Demo(https://codepen.io/airen/embed/mdVXQON)

同样在一些卡片类布局中运用:

4881c33f4911da578b8db62f9b0eb5e5.png

Demo(https://codepen.io/airen/embed/MWKQzmE)

如果需求有所调整,比如在Flex项目 或 Grid项目的子元素高度和容器高度相同。

                /* CSS */.flex__container {    display: flex;}.content {    height: 100%}// 或.grid__container {    display: grid;    grid-auto-flow: column;}.content {    height: 100%;}

效果如下:

500eeeb0c02f43e40368a85c3bfe956d.png

Demo(https://codepen.io/airen/embed/jOWZdbo)

基于Sticky Footer


首先用下图来描述什么是Sticky Footer布局效果:

e7b2c3e25f54da4e90c4b58f4e840543.png

Sticky Footer实现方案和等高、垂直居中一样,同样有很多种方案可以实现(//css-tricks.com/couple-takes-sticky-footer/)。

比如像下面这样的结构:

先来看Flexbox布局模块中的实现方案:

body {    display: flex;    flex-direction: column;}footer {    margin-top: auto;}

1d9271a1d4669cbfa1a5fac730bbc0e7.png

Demo(https://codepen.io/airen/embed/bGELzYy)

可以尝试着在main区域右下角向下拖动,改变主内容区域的高度,你会发现“当内容不足一屏时,会在页面的最底部,当内容超出一屏时,会自动往后延后”。

在Flexbox布局中,还可以在区域上设置下面的样式,达到相等的效果:

body {    display: flex;    flex-direction: column;}main {    flex: 1 0 auto;}

效果如下:

35f0e7a740a8f6d8e639266861a96df6.png

Demo(https://codepen.io/airen/embed/zYrRXmY)

中的flex: 1 0 auto相当于是:

main {    flex-grow: 1; /*容器有剩余空间时,main区域会扩展*/    flex-shrink: 0; /*容器有不足空间时,main区域不会收缩*/    flex-basis: auto; /*main区域高度的基准值为main内容自动高度*/}

如果你想省事的话,可以在main上显式设置flex-grow:1,因为flex-shrinkflex-basis的默认值为1auto

在CSS Grid布局中我们可以借助1fr区域根据Grid容器剩余空间来做计算。

.grid__container {    display: grid;    grid-template-rows: auto 1fr auto;}

效果如下:

7f32c8b52ac64a2e8251159bbe036991.png

Demo(https://codepen.io/airen/embed/MWKQRxd)

均分列


在Web布局中,很多时候会对列做均分布局,最为常见的就是在移动端的底部Bar,比如下图这样的一个效果:

88fbd867ce8f3ffe210623abba6d6b2a.png

在Flexbox和Grid还没出现之前,如果希望真正的做到均分效果,可以用100%(或100vw)除以具体的列数。比如:

<container>    <column>column>    <column>column>    <column>column>container>/* CCSS */.container {    inline-size: 50vw;    min-inline-size: 320px;    display: flex-row;}.column {    float: left;    width: calc(100% / 3);}

效果如下:

5189b16d4ca84f53fdbe82429e60bf18.png

Demo(https://codepen.io/airen/embed/LYGQoxL)

通过浏览器调试器中可以发现,现个列的宽度都是相等的:

a11169427bfaaead2a57c9b5934a364f.gif

在Flexbox和Grid布局中,实现上面的效果会变得更容易地多。先来看Flexbox中的布局:

<flex__container>    <flex__item>flex__item>    <flex__item>flex__item>    <flex__item>flex__item>flex__container>/* CSS */.flex__container {    inline-size: 50vw;    display: flex;}.flex__item {    flex: 1;}

效果如下:

3fe35ebf4274d4b35860710731760b9a.png

Demo(https://codepen.io/airen/embed/yLevWEe)

在Flexbox布局模块中,当flex取的值是一个单值(无单位的数),比如示例中的flex:1,它会当作显式的设置了flex-grow: 1。浏览器计算出来的flex

1f22803aa396ee6007330eb352739fb4.png

接下来看Grid中如何实现上例的效果:

<grid__container>    <grid__item>grid__item>    <grid__item>grid__item>    <grid__item>grid__item>grid__container>/* CSS */.grid__container {    display: grid;    grid-template-columns: repeat(3, 1fr); /*这里的3表示具体的列数*/}

最终的效果是相同的:

913aaf59564e46c768c00bbb85436149.png

Demo(https://codepen.io/airen/embed/NWxyVQP)

这样的布局方式也适用于其他的布局中。但不管是Flexbox还是Grid布局中,都存在一定的缺陷,当容器没有足够的空间容纳Flex项目(或Grid项目)时,Flex项目或Grid项目会溢出(或隐藏,如果Flex容器或Grid容器显式设置了overflow:hidden):

1e5ddfde2eb24bf60d42bc142caeed5f.gif

修复这种现象最简单的方式是在Flex容器或Grid容器显式设置一个min-width(或min-inline-size):

.flex__container {    min-inline-size: 300px;}

不过话又说回来,比如我们的Flex项目(或Grid项目)是一个卡片,每张卡片宽度是相等之外,更希望容器没有足够空间时,Flex项目(或Grid项目)会自动断行排列。

我们继续通过示例向大家展示。先来看Flexbox实现方案:

.flex__container {    display: flex;    flex-wrap: wrap;}.flex__item {    flex: 0 1 calc((100vw - 18vh) / 4); /* calc(100vw -18vh) / 4 是flex-basis的基准值 */}

86da53b9e5fb259621faccf6ad31f019.png

Demo(https://codepen.io/airen/embed/dyGdBpw)

你可以尝试着调整浏览器的视窗宽度,当浏览器的视窗越来越小时,Flex容器宽度也就会越来越小,当Flex容器小到没有足够的空间容纳四个Flex项目(就此例而言),那么Flex项目就会断行排列:

ffe3d7eadeea52167d8661f096f2b394.gif

基于该例,如果把Flex项目的flex值改成:

.flex__item {    flex: 0 0 400px;}

这个时候,当Flex容器没有足够空间时,Flex项目会按flex-basis: 400px计算其宽度,Flex容器没有足够空间时,Flex就会断行:

9dbc1a84f5061259977effe877c2c7bb.png

反过来,如果Flex项目的值flex改成:

.flex__item {    flex: 1 0 400px;}

当Flex容器没有足够空间排列Flex项目时,Flex项目会按flex-basis: 400px计算其宽度,Flex会断行,并且同一行出现剩余空间时,Flex项目会扩展,占满整个Flex容器:

4b88742dfc2cdeca3dafdf85c5915099.png

在Grid中实现类似的效果要更复杂一点。可以使用repeat()函数,1fr以及auto-fit等特性:

.grid__container {    display: grid;    grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));    gap: 2vh;}

效果如下:

163a154d403827d050a21d3c31c98fb5.png

Demo(https://codepen.io/airen/embed/RwrQzeN)

如果你对这方面知识感兴趣的话,还可以移步阅读《Container Query Solutions with CSS Grid and Flexbox(//moderncss.dev/container-query-solutions-with-css-grid-and-flexbox/)》一文。

其实在Grid中与auto-fit对比的值还有一个叫auto-fill。但两者的差异是非常地大,用下图来描述auto-fitauto-fill的差异:

c72f98c8a2452f05f5cc3f5890e323ef.png

另外这种方式也是到目前为止一种不需要借助CSS媒体查询就可以实现响应式布局效果。

圣杯布局


圣杯布局(Holy Grail Layout)(//en.wikipedia.org/wiki/Holygrail(web_design))是Web中典型的布局模式(//alistapart.com/article/holygrail/)。看上去像下图这样:

4f4fe247a4681326ba5874b92ad9adff.png

对于圣杯布局而言,HTML结构是有一定的要求,那就是内容为先:

<header>header><main>    <article>article>     <nav>nav>    <aside>aside>main><footer>footer>

在这里主要还是和大家一起探讨,如何使用Flexbox和Grid布局模块来实现圣杯布局。先来看Flexbox实现方案:

body {    width: 100vw;    display: flex;    flex-direction: column;}main {    flex: 1;    min-height: 0;    display: flex;    align-items: stretch;    width: 100%;}footer {    margin-top: auto;}nav {    width: 220px;    order: -1;}article {    flex: 1;}aside {    width: 220px;}

效果如下:

348e8b39304fe29b1b190ccdacd3dd61.png

Demo(https://codepen.io/airen/embed/rNxJXYb)

通过在navasidearticle上显式设置order的值,可以很好的控制这三个区域的布局顺序。比如说,希望之前排列,只需要在上面的示例基础上做一点点调整:

nav {    order: 0;}aside {    order: -1;}

效果如下:

8cf756d8e4cca8020e5e950f6514e2b3.png

注意,order的默认值为0,值越大越排在后面!

在上例的基础上,借助CSS媒体对象的特性,可以很容易实现响应式的圣杯布局效果:

@media screen and (max-width: 800px) {    main {        flex-direction: column;    }    nav, aside {        width: 100%;    }}

效果如下:

a1f4ea24a72d274d71b220e070110315.png

Demo(https://codepen.io/airen/embed/gOPvVZX)

尝试着拖动浏览器来改变视窗大小,你可以看到如下图的效果:

a03959c26b70a14de4ed29ac649d3763.gif

在Grid布局模块中,实现圣杯布局要比Flexbox布局模块中更容易,而且更灵活。在CSS Grid布局模块中,HTML结构可以更简洁:

<body>    <header>header>    <main>main>    <nav>nav>    <aside>aside>    <footer>footer>body>

在CSS方面有很多种方案可以实现圣杯布局效果。我们先来看第一种:

body {    display: grid;    grid-template: auto 1fr auto / 220px 1fr 220px;}header {    grid-column: 1 / 4;}main {    grid-column: 2 / 3;    grid-row: 2 / 3;}nav {    grid-column: 1 / 2;    grid-row: 2 / 3;}aside {    grid-column: 3 / 4;    grid-row: 2 / 3;}footer {    grid-column: 1 / 4;}

效果如下:

a6ff2228b0cdec6784f5d42a8ca98043.png

Demo(https://codepen.io/airen/embed/PoZRYPa)

上面示例采用的是网格线来给每个区域进行定位的:

42500300750c23cca908f536ecd22152.png

和Flexbox布局类似,在媒体查询中可以改变每个网格区域的位置:

@media screen and (max-width: 800px) {    body {        grid-template-rows: auto;        grid-template-columns: auto;    }    header,    main,    nav,    aside,    footer {        grid-column: 1 / 2;        min-height: auto;    }    main {        grid-row: 3 / 4;        margin: 0;    }    nav {        grid-row: 2 / 3;    }    aside {        grid-row: 4 / 5;    }    footer {        grid-row: 5 / 6;    }}

b225ec59638e5544382b13c07b2d0993.png

Demo(https://codepen.io/airen/embed/vYLRBaa)

除了grid-template(即grid-template-columnsgrid-template-rows)之外,在Grid布局中还可以使用grid-areagrid-template-areas属性的结合,也能很方便的实现CSS圣杯布局。基于上面的示例上,只需要把你的CSS调整为:

body {    display: grid;    grid-template-areas:        "header header header"        "nav main aside"        "footer footer footer";}header {    grid-area: header;}main {    grid-area: main;}nav {    grid-area: nav;}aside {    grid-area: aside;}footer {    grid-area: footer;}@media screen and (max-width: 800px) {    body {        grid-template-areas:            "header"            "nav"            "main"            "aside"            "footer";    }}

效果如下:

948881635d8db136f31160e71459040a.png

Demo(https://codepen.io/airen/embed/LYGdRrG)

你可能发现了它们之间的差异性:

cd2ca0c2888f7f90288d67a57fe86c9b.png

后面这个示例中,区域宽度相等。这是因为我们示例中通过grid-template-areas来声明网格,在使用grid-template-areas创建网格时,其实也隐式的创建了网格线,只不过他和grid-template不同的是grid-template可以显式的指定网格轨道大小,而grid-template-areas在该示例中相当于网格轨道大小都是1fr

a7898ab7345231edf019b4637d67dfe6.png

如果我们希望的区域变得更大,那么可以在grid-template-areas上做个调整:

body {    display: grid;    grid-template-areas:        "header header header header header"        "nav main main main aside"        "footer footer footer footer footer";}

效果如下:

3f7c5876ec6643762e24a8e633dfa1f7.png

Demo(https://codepen.io/airen/embed/QWymKYZ)

这个时候网格区域的划分像下图这样:

fa3e4aad9abf156181f61f8cf1fc3da6.png

虽然在效果有所调整了,但还是均分状态。更好的解决方案是,将grid-template-areasgrid-template结合起来使用:

body {    display: grid;    grid-template-areas:        "header header header"        "nav main aside"        "footer footer footer";    grid-template-columns: 220px 1fr 220px;    grid-template-rows: auto 1fr auto;}header {    grid-area: header;}main {    grid-area: main;}nav {    grid-area: nav;}aside {    grid-area: aside;}footer {    grid-area: footer;}@media screen and (max-width: 800px) {    body {        grid-template-areas:            "header"            "nav"            "main"            "aside"            "footer";        grid-template-columns: 1fr;        grid-template-rows: auto auto 1fr auto auto;    }    main {        margin-left: 0;        margin-right: 0;    }}

效果如下:

d6941c42c8e0b21283b7f70c5810fbc2.png

Demo(https://codepen.io/airen/embed/OJMvRev)

你可以发现,这个时候,网格线的区域的命名像下图这样:

310a6f71a4ff9bd374b1716ddf41a7e9.png

12列网格布局


12列网格布局最早是由960.gs提出的网格布局系统(//960.gs/):

3ae4dbccf13882fbc1bdbbd90fbef19d.png

12列网格布局在设计系统和CSS Framework中经常使用,比如业内经典的Bootstrap(//getbootstrap.com/)就采用了12列网格布局系统:

1b40a2cbeaf40536133eca06f846dbb3.png

在社区中也有很多在线工具,帮助我们快速构建12列网格系统,比如 Free CSS Grid Tools & Resources For Developers(//1stwebdesigner.com/free-css-grid-tools-resources/) 一文中罗列的工具。

e146f23323a24b9a761b38c2dfc95428.png

Demo (http://paulhebertdesigns.com/gridley/)

不过这里主要是想和大家一起看看在Flexbox和Grid布局模块中是如何实现12列的网格布局系统。

先来看Flexbox布局模块。12列网格布局的HTMl结构一般类似于下面这样:

<flex__grid>    <flex__row>        <flex__item col4>flex__item col4>        <flex__item col4>flex__item col4>        <flex__item col4>flex__item col4>    flex__row>flex__grid>

注意,12列网格中,一般同一行的列数值和刚好等于12。比如上面的HTML结构,行中有三列,每列的宽度刚好四个网格宽度加两个列间距。并且在计算的时候有一套成熟的计算公式:

8305feb21136967342d1e2c9fd8f4f34.png

而且还设计上也会有所差异,比如说距离容器两侧有没有间距等:

b7917aafa03a1a6d29f8f186c67c3ae0.png

这些的差异对于计算公式和样式代码的设计都略有差异。我们用其中一个为例:

:root {    --gutter: 10px;    --columns: 12;    --span: 1;}.flex__container {    display: flex;    flex-direction: column;    padding-left: var(--gutter);    padding-right: var(--gutter);}.flex__row {    display: flex;    margin-left: calc(var(--gutter) * -1);    margin-right: calc(var(--gutter) * -1);}.flex__row + .flex__row {    margin-top: 2vh;}.flex__item {    flex: 1 1        calc((100% / var(--columns) - var(--gutter)) * var(--span));    margin: 0 var(--gutter);}.flex__item1 {    --span: 1;}.flex__item2 {    --span: 2;}.flex__item3 {    --span: 3;}.flex__item4 {    --span: 4;}.flex__item5 {    --span: 5;}.flex__item6 {    --span: 6;}.flex__item7 {    --span: 7;}.flex__item8 {    --span: 8;}.flex__item9 {    --span: 9;}.flex__item10 {    --span: 10;}.flex__item11 {    --span: 11;}.flex__item12 {    --span: 12;}

你会看到的效果如下:

e17e39b4b12685ea6100534fcfdf0769.png

Demo(https://codepen.io/airen/embed/YzwaxwX)

在该示例中采用了CSS自定义属性相关的特性,让整个计算变得更容易一些。

对于使用CSS Grid布局模块来实现12列网格布局,相对而言,不管是HTML结构还是CSS代码都会更简易一些。在使用CSS Grid布局模块实现12列网格布局,将会运用到repeat()minmax()gapfr等特性。具体的来看一个示例吧。

<grid__container>    <grid__item>grid__item>grid__container>

我们来看CSS代码:

  • 使用fr将网格均分为相等的值,即每列宽度都是1fr;配合repeat()函数,即repeat(12, 1fr)创建了12列网格

  • 使用gap可以用来控制网格之间的间距

  • 配合minmax()还可以设置网格最小值

具体的代码如下:

:root {    --columns: 12;    --gap: 10px;    --span: 1;}.grid__container {    display: grid;    grid-template-columns: repeat(var(--columns), 1fr);    grid-template-rows: 1fr;    gap: var(--gap);    padding-left: calc(var(--gap) / 2);    padding-right: calc(var(--gap) / 2);}.grid__item {    min-block-size: 10vh;    grid-column: span var(--span);}.col1 {    --span: 1;}.col2 {    --span: 2;}.col3 {    --span: 3;}.col4 {    --span: 4;}.col5 {    --span: 5;}.col6 {    --span: 6;}.col7 {    --span: 7;}.col8 {    --span: 8;}.col9 {    --span: 9;}.col10 {    --span: 10;}.col11 {    --span: 11;}.col12 {    --span: 12;}

你将看到的效果如下:

4b562ed84581de34d46bb89d94548323.png

Demo(https://codepen.io/airen/embed/yLeKPPb)

就该示例而言,grid-template-columns: repeat(12, 1fr)创建网格如下图所示:

34e7cae25bd49aa3f81d99639d7f7b26.png

除了上述这种粗暴的方式,还可以更灵活一些,将auto-fitminmax()以及grid-auto-flow: dense等来创建:

.grid__container {    padding: 1em;    display: grid;    grid-template-columns: repeat(auto-fit, minmax(60px, 1fr));    gap: 1em;    grid-auto-flow: dense;}

对于.grid__item可以通过grid-columngrid-row来控制网格项目的位置:

6a06564b349a2b1e50b97990cdd72ac9.png

Demo(https://codepen.io/airen/embed/QWymabq)

加上grid-auto-flow: dense会根据Grid容器空间,Grid项目会自动流到合适的位置:

95e33b45ac6d93d1b63b3ce5199eb93e.gif

这种布局对于杂志类的布局非常的适用。有关于这方面更详细的介绍可以阅读@Keir Watson的《Responsive Grid Magazine Layout in Just 20 Lines of CSS(//css-tricks.com/responsive-grid-magazine-layout-in-just-20-lines-of-css/)》一文。

两端对齐


在Web布局中时常碰到两端对齐的需求。在Flexbox布局中,时常在Flex容器中显式设置justify-content的值:

.flex__container {    display: flex;    flex-wrap: wrap;    justify-content: space-between;    width: 100%;}

但在末尾行,如果和前面行的个数不相同(Flex项目)就会出现下图这样的效果:

b962cd139a641b94320e13caf65dd435.png

像上图这样的效果,并不是我们所需要的,因为我们希望在最后一行的Flex项目不足够排列满一行时,希望Flex项目一个紧挨一个的排列:

78746f5959009c4bd558824b76bea9b2.png

在Flexbox要实现上图这样的效果,只需要在Flex容器中添加一个伪元素:

.flex__container::after {    content: "";    display: flex;    flex: 0 1 32vw;}

注意,伪元素的flex-basis建议设置的和卡片的flex-basis(或宽度)等同。这个时候你将看到像下面这样的示例:

82ccb45b7ed186e88a9836516092cff2.png

Demo(https://codepen.io/airen/embed/QWymaam)

不过这种方式也不是最佳的方式,当末尾行的个数不只少一个时,就会出现下图这样的效果:

e05e380a9dc70054d8aab99a8ddedeea.png

面对这样的场景,我们需要给Flex容器添加额外的空标签元素:

占位符元素数量 = 每行最大的列数 - 2

但是gap属性出现之后,要实现这样的效果就不难了:

body {    padding: 1vh;}.flex__container {    display: flex;    flex-wrap: wrap;    gap: 2vh;    width: 100%;}.flex__item {    flex: 0 1 calc((100vw - 8vh) / 4);}

效果如下:

9aaeee68af4d1703b434f68cd454b93f.png

Demo(https://codepen.io/airen/embed/YzwaYBN)

注意,gap运用在Flexbox中到目前为止,仅得到了Firefox浏览器的支持。上面的示例,使用Firefox浏览器,你看到的效果如下:

7ecec1f02ff425b2d230e6a26842c1b9.png

在CSS Grid布局中,就可以直接使用gap

body {    padding: 1vh;}.grid__container {    display: grid;    grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));    gap: 1vh;}

效果如下:

5e23055b81b609f7907c47e1d73a0a8a.png

Demo(https://codepen.io/airen/embed/eYJMVbz)

选择最佳的值


很多时候,针对不同的场景,设计师会为我们提供不同的设计风格,比如元素大小:

d58d4b40a37566d4e691497c0b3ee70c.png

随着clam()函数的到来,这一切都变得容易地多。

clam()函数接受三个参数,即 clam(MIN, VAL, MAX),其中MIN表示最小值,VAL表示首选值,MAX表示最大值。它们之间:

  • 如果VALMINMAX之间,则使用VAL作为函数的返回值;

  • 如果VAL大于MAX,则使用MAX作为函数的返回值;

  • 如果VAL小于MIN,则使用MIN作为函数的返回值

我们来看一个示例:

.element {    /**    * MIN = 100px    * VAL = 50vw ➜ 根据视窗的宽度计算    * MAX = 500px    **/    width: clamp(100px, 50vw, 500px);}

比如浏览器视窗现在所处的位置是1200px的宽度,那么.element渲染的结果如下:

1bffa1509d330a839290bac11f829763.png

这个时候.element元素的width500px。此时,clamp(100px, 50vw, 500px)相当于clamp(100px, 600px, 500px),对应的VAL值是600px,大于MAX值,那么这个时候clamp()函数返回的值是MAX,即500px,这个时候.elementwidth值就是500px(即MAX的值)。

如果我们把浏览器视窗缩小至760px

5163fcc8d436904ccfb2d49654c438fe.png

这个时候.element元素的width50vw。此时,clamp(100px, 50vw, 500px)相当于clamp(100px, 380px, 500px),对应的VAL值是380px,该值大于MIN值(100px),小于MAX值(500px),那么这个时候clamp()函数返回的值是VAL,即50vw,这个时候.elementwidth值就是50vw(即VAL的值)。

如果继续将浏览器的视窗缩小至170px:

df71e139891d23824cbcd7d9f8db20c3.png

这个时候.element元素的width100px。此时,clamp(100px, 50vw, 500px)相当于clamp(100px, 85px, 500px),对应的VAL值是85px,该值小于MIN值(100px),那么这个时候clamp()函数返回的值是MIN,即100px,这个时候.elementwidth值就是100px(即MIN的值)。

就该示例而言,clamp(100px, 50vw, 500px)还可以这样来理解:

  • 元素.element的宽度不会小于100px(有点类似于元素设置了min-width: 100px)

  • 元素.element的宽度不会大于500px(有点类似于元素设置了max-width: 500px)

  • 首选值VAL50vw,只有当视窗的宽度大于200px且小于1000px时才会有效,即元素.element的宽度为50vw(有点类似于元素设置了width:50vw)

具体效果如下占击这里查看(https://codepen.io/airen/embed/pojVpJv)。

Logo图标的对齐


我想你在Web开发中可能碰到过类似下图的这样的场景:

8e3d396bf54c2d49663f87fd8154d03a.png

正像上图所示,Logo图像的有大有小(宽度和高度都不一样)。面对这样的业务场景,很多时候都希望设计师能提供相同尺寸的图像。但这样势必会影响Logo图像的外观。

前段时间看到@Ahmad Shadeed专门写了一篇博文《Aligning Logo Images in CSS(//ishadeed.com/article/aligning-logos-css/)》,就是介绍如何实现上图这样的布局效果。

其实实现这样的布局效果,主要运用到的就是CSS的object-fit属性,而这个属性早在多年前就得到了各大主流浏览器的支持。

这里我们用一个简单的示例,来看看具体实现过程。先来看HTML结构:

<ul class="brands">    <li class="brands__item">        <a href="#">            <img src="img/logo.png" alt="">        a>    li>    <li>  li>ul>

居中对齐前面已经介绍过了,这里主要是看图像大小方面的处理:

.brands {    display: grid;    grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));    grid-gap: 1rem;}.brands__item {    background: #eee;}.brands__item a {    display: flex;    justify-content: center;    align-items: center;    height: 100%;}.brands__item img {    width: 130px;    height: 75px;    object-fit: contain;}

这样就能实现上图的效果。你可能发现了,有些Logo图像带有背景颜色,如果让效果更好一些,可以把CSS混合模式相关的特性运用进来:

.brands__item img {    width: 130px;    height: 75px;    object-fit: contain;    mix-blend-mode: multiply;}

这个时候,你看到的效果如下:

61dad8d849c7175d026964de98121e42.png

object-fit除了取值contain之外,还有其他几个值,具体的可以看这个示例(https://codepen.io/airen/embed/VweXXoo):

55eb2ee9c029716b51f47319f5eab9cc.png

其实这个方案也适用于产品图片,人物头像等布局。

小结


文章中主要介绍了Web中一些布局的实现思路和具体方案。其实文章提到的效果,比如水平垂直居中、等高布局、平均分布列和Sticky Footer等,在CSS中一直有多种解决方案,只不过随着CSS Flexbox布局模块和CSS Grid布局模块的到来,实现这些效果变得更为灵活和简洁。

当然,文章中提到的只是一些最为常见一些效果,其实在Web布局中,特别是Flexbox布局和Grid布局中还存在很多有意思的东西,只不过因为篇幅的时间没有一一罗列。如果你感兴趣可以再挖掘一些出来,如果你在这方面有更好的经验或方案,欢迎在下面的评论中分享。最后希望这篇文章对你平时的工作有所帮助。

✿  拓展阅读

9f045ea8a79baf6a3456f246f12370c8.png

5279c567535c4c0ffc2f449211a7697a.png7817443103e7b08adaa9f86960290b4a.png作者|廖伟华(大貘)编辑|橙子君出品|阿里巴巴新零售淘系技术efb78a9642c27705e477cca6ef76623b.png9b4d551e2105e5b1330589a5bfd77fb9.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/561234.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

复合消隐信号的作用_南大《AFM》:可拉缩、粘合、导电的双信号柔性彩色薄膜...

导读&#xff1a;本文得到了一种可伸缩、可粘合、可自修复、可导电的双信号柔性电子结构彩色薄膜&#xff0c;具有很大的应用潜力。柔性电子设备在各种应用中发挥着不可忽视的作用&#xff0c;如健康监控、感觉皮肤、可植入设备等。柔性电子材料的研究已取得了很大进展&#xf…

三轴加速度传感器和六轴惯性传感器_一文读懂汽车MEMS惯性传感器的七大应用(上)...

本文中&#xff0c;我们将研究汽车MEMS惯性传感器的应用&#xff0c;描述它们的工作原理&#xff0c;并讨论如何利用MEMS惯性传感器来实现更大的应用改进。 当前&#xff0c;微机电系统&#xff08;MEMS&#xff09;传感器已被大多数汽车工程师视为尖端技术或边缘技术&#xff…

criteria函数_干货铺 | 二级MS office考试中一些常考函数(2)

同步文章&#xff1a;二级MS office考试中一些常考函数&#xff08;2&#xff09;1.AVERAGE(Number1,Number2,…)函数——计算平均值函数&#xff1a;参数解释&#xff1a;Number1&#xff0c;number2&#xff0c;...是要计算平均值的 1&#xff5e;255 个参数。2.averageif(ra…

html中图片透明度渐变效果,css怎么设置透明度渐变?

css怎么设置透明度渐变&#xff1f;下面本篇文章给大家介绍一下使用CSS设置透明度渐变效果的方法。有一定的参考价值&#xff0c;有需要的朋友可以参考一下&#xff0c;希望对大家有所帮助。css怎么设置透明度渐变&#xff1f;在CSS中可以使用linear-gradient()函数配合rgba()来…

oc 画一个圆弧_SolidWorks一步扫描特征,就可以画出一个螺母,你有思路吗

建模过程&#xff1a;1.在【上视基准面】画一个六边形。(引导线)1-1.圆角&#xff0c;半径&#xff1a;2 &#xff0c;框选六边形。2.在【前视基准面】画草图如下&#xff1a;(轮廓)2-1.左侧画一段竖直构造线&#xff0c;端点与圆弧穿透几何关系。3.【线段】草图绘制点&#xf…

python默认安装位置_如何更改python中pip的默认安装路径

具体方法&#xff1a; 1、查看 site.py 文件的位置(一般在python安装目录的\Lib下&#xff09;&#xff0c;可使用指令查询&#xff1a;python -m site -help2、打开site.py文件&#xff0c;更改 USER_BASE 和USER_SITE 的路径即可。其中 USER_BASE 和USER_SITE其实就是用户自定…

java被电脑阻止怎么办_学电脑,一定要记住的6个常用命令,它能让你快速成为电脑达人...

电脑对于我们所有人来说都是一项非常伟大的发明。目前&#xff0c;在我们的生活中它已经成为了一个不可或缺的工具。时时围绕在我们的周围&#xff0c;如果离开电脑&#xff0c;可以说很多人都将寸步难行&#xff0c;科技也得不到发展。那么作为电脑的初学者&#xff0c;我们该…

动词ing形式的5种用法_英语语法这样学就对了!动词-ing结构的特征和四种形式是?...

想彻底学好英语一定要善于总结语法&#xff01;动词-ing结构的特征和四种形式都是什么&#xff1f;想彻底学好英语&#xff0c;语法这一关是一定要过的。我将通过这个平台定期更新实用、常用的英语语法知识解读&#xff0c;直至覆盖完全部的英语语法知识点&#xff0c;使你通过…

mysql 数据迁移_【AWS 功能】Mysql 数据库迁移至Amazon RDS方案

今天&#xff0c;我们讲讲如何使用源MySQL数据库执行数据库迁移到MySQL数据库的目标Amazon RDS的方案&#xff0c;同时由于(源和目标数据库引擎是相同的)——模式结构、数据类型和数据库代码在源和目标数据库之间是兼容的&#xff0c;这意味着这种迁移不需要任何模式转换。数据…

eclipse run on server 点不了finish_分享点经验 | springboot入门及编码

点击蓝字关注我们AMP很多新人在刚刚接触后端开发的时候&#xff0c;可能对springboot的概念、如何快速上手一个springboot项目多多少少有些一知半解&#xff1b;此外写出来的代码也因为不够规范而可读性较低&#xff0c;导致后期难以维护。本文旨在站在新手的视角&#xff0c;尽…

mac redis 客户端_分享一个免费好用的Redis桌面客户端

今天波波为做开发的朋友们分享一个免费好用的Redis桌面客户端。这个工具纯属机缘巧合下发现的&#xff0c;前几天波波在开发一个物联网平台&#xff0c;硬件通信部分用了Workman Gateway来负责通信和消息推送&#xff0c;结果因为自己把官方的文档理解错误&#xff0c;遇到了一…

实测实量数据表格_建筑工程质量实测实量操作手册,130页PPT下载!

来源&#xff1a;百度文库版权归原作者所有文件下载方式在最后第一篇 总 则1、适用范围2、取样总则第二篇 尺差控制篇1、混凝土结构工程2、实测实量数据、水平基准线上墙3、砌体工程4、抹灰工程5、设备安装6、涂饰工程7、饰面墙砖(石材)工程8、地面饰面砖(石材)工程9、吊…

0018计算机基础知识,0018 0019计算机应用基础上机试题

满意答案pgeqanyyafe2013.02.23采纳率&#xff1a;51% 等级&#xff1a;12已帮助&#xff1a;6328人有2套&#xff1a;复制发给你&#xff1f; 还是通过QQ发给你呢&#xff1f; 还是给你发到邮箱呢&#xff1f;第一套&#xff1a;《计算机应用基础》上机考试试题 姓名&…

java接口测试工具_【分享】接口工具对比(apipost、jmeter、postman、swagger等)

一、接口都有哪些类型&#xff1f;接口一般分为两种&#xff1a;1.程序内部的接口 2.系统对外的接口系统对外的接口&#xff1a;比如你要从别的网站或服务器上获取资源或信息&#xff0c;别人肯定不会把 数据库共享给你&#xff0c;他只能给你提供一个他们写好的方法来获取数据…

用flash做古诗动画_带孩子用两张A4纸做动画(内附资源可下载)

不要让孩子在成长过程中丢失了对自然的好奇心&#xff0c;在自然科学(物理&#xff0c;化学&#xff0c;生物&#xff0c;天文......)的实验中快乐成长&#xff0c;热爱生活&#xff0c;保护环境&#xff0c;探索精彩世界。科学爸爸的孩子从2014年四岁多开始对科学产生了浓厚兴…

promise的状态以及api介绍_2019年,盘点一些我出过的前端面试题以及对求职者的建议

笔者虽然曾经也面试过很多求职者,但是对于前端的笔试和面试,我觉得并不能体现一个人的真实能力,所以建议大家多修炼前端真正的技术.对于前端面试题,之前也承诺过读者要出一篇,笔者大致总结一下曾经面试的题目.后续不会再出面试题,而是聚焦于一些真正的,有利于成长性的技术文章和…

otis电梯服务器tt使用说明_南充私人电梯

南充私人电梯&#xff0c;成都蒂澳机电放心产品&#xff0c;并在麓山国际社区、麓湖别墅、蔚蓝卡地亚、城南官邸、城南逸家、复地御香山、万科五龙山、保利198、美城悦荣府、三利宅院、维也纳森林别墅、乐山御墅、华侨城纯水岸(东岸)、芙蓉古城等知名别墅楼盘均有大量成功案例。…

计算机上课创意互动游戏初中,16个课前热身小游戏:让每一堂课都充满新鲜感...

课堂正式开始之前&#xff0c;设置热身游戏&#xff0c;教学效果会更佳。它可以达到两个目的&#xff1a;一是把学生的注意力吸引到课堂&#xff1b;二是通过游戏自然过渡到课堂内容&#xff0c;增加课堂趣味性和学生参与感。受新冠病毒的影响&#xff0c;居家学习席卷全国&…

ros c++ 代码说明文档_减少运维工作量,如何通过 ROS 轻松实现资源编排新方式...

在日常工作中&#xff0c;我们一定遇到过需要快速构建系统的工作情形&#xff1a;作为资源管理人员&#xff0c;需要接收一定数量以及配置的资源申请&#xff0c;这些申请要求网络、存储设备按需到位&#xff1b;作为开发人员&#xff0c;需要将一套开发环境&#xff0c;复制一…

华硕和梅林系统哪个好_RUSHCRM:定制CRM软件系统哪个好?

Crm系统是一个可以帮助企业获得、维护以及提升客户价值的系统&#xff0c;并且做到以客户为中心的管理模式。但是有不少企业在选择crm软件系统的过程中&#xff0c;会发现在国内crm系统的市场中&#xff0c;绝大多数crm系统的功能都不能完全满足企业的需求&#xff0c;那么就需…