- 前言
- 一、介绍 CSS 布局
- 1、正常布局流
- 2、display 属性
- 3、弹性盒子
- (1)设置 display:flex
- (2)设置 flex 属性
- 4、Grid 布局
- (1)设置 display:grid
- (2)在网格内放置元素
- 5、浮动
- 6、定位
- 7、表格布局
- 8、多列布局
- 总结
前言
由于有很多知识非常符合直觉或者和其他语言有通用性,因此个人觉得不需要全部记下来,本篇只记录一些个人觉得需要注意或单独记忆的知识点。
同时为了提高效率和减少对不重要内容的时间投入,会考虑更加精简
本篇是布局概览,下一篇会把各部分再详细整理
一、介绍 CSS 布局
这个模块中将涉及更多关于页面布局技术的细节:
- 正常布局流
display
属性- 弹性盒子
- 网格
- 浮动
- 定位
- CSS 表格布局
- 多列布局
1、正常布局流
正常布局流(normal flow)指在不对页面进行任何布局控制时,浏览器默认的 HTML 布局方式。
出现在另一个元素下面的元素被描述为块元素,与出现在另一个元素旁边的内联元素不同,内联元素就像段落中的单个单词一样
块元素内容的布局方向被描述为块方向。块方向在英语等具有水平书写模式(writing mode) 的语言中垂直运行。它可以在任何垂直书写模式的语言中水平运行。对应的内联方向是内联内容(如句子)的运行方向
下列布局技术会覆盖默认的布局行为:
display
属性:标准的 value,比如block
,inline
或者inline-block
元素在正常布局流中的表现形式。 接着是全新的布局方式,通过设置display的值,比如CSS Grid
和Flexbox
- 浮动:应用
float
值,例如left
能让块级元素互相并排成一行,而不是一个堆叠在另一个上面 position
属性:允许精准设置盒子中的盒子位置,正常布局流中默认为static
,使用其他值可以引起元素不同布局方式,比如将元素固定到浏览器视口的左上角- 表格布局:表格的布局方式可以用在非表格内容上,可以使用
display:table
和相关属性在非表元素上使用 - 多列布局:可以让块按列布局,比如报纸的内容就是一列一列排布的
2、display 属性
除了可以通过将一些内容从block
转换为inline
(反之亦然)来更改默认表示形式之外,还有一些更大的布局方法以display值开始。但是,在使用这些属性时,通常需要调用其他属性。在讨论布局时,对我们来说最重要的两个值是 display: flex
和 display: grid
3、弹性盒子
Flexbox(Flexible Box Layout Module)是 CSS 弹性盒子布局模块的缩写。用于创建横向或纵向的一维页面布局。在需要进行 flex 布局的父元素上应用display:flex
,所有直接子元素都将会按照 flex进行布局
(1)设置 display:flex
下面这些 HTML 标记描述了一个 class 为wrapper的容器元素,它的内部有三个<div>
元素。它们在我们的英文文档当中,会默认地作为块元素从上到下进行显示
<div class="wrapper"><div class="box1">One</div><div class="box2">Two</div><div class="box3">Three</div>
</div>
现在,当我们把display: flex
添加到它的父元素时,这三个元素就自动按列进行排列。这是由于它们变成了flex 项 (flex items),按照 flex 容器(也就是它们的父元素)的一些 flex 相关的初值进行 flex 布局:它们整整齐齐排成一行,是因为父元素上flex-direction
的初值是row
。它们全都被拉伸至和最高的元素高度相同,是因为父元素上align-items
属性的初值是stretch
。这就意味着所有的子元素都会被拉伸到它们的 flex 容器的高度,在这个案例里就是所有 flex 项中最高的一项。所有项目都从容器的开始位置进行排列,排列成一行后,在尾部留下一片空白
.wrapper {display: flex;
}
结果如下
(2)设置 flex 属性
除了上述可以被应用到 flex 容器的属性以外,还有很多属性可以被应用到 flex 项 (flex items) 上面。这些属性可以改变 flex 项在 flex 布局中占用宽/高的方式,允许它们通过伸缩来适应可用空间
比如在所有子元素上添加flex
属性并赋值为1
,这会使得所有子元素都伸展并填充容器,而不是在尾部留下空白
.wrapper {display: flex;
}.wrapper > div {flex: 1;
}
<div class="wrapper"><div class="box1">One</div><div class="box2">Two</div><div class="box3">Three</div>
</div>
效果如下
更多信息在下面专门的 flexbox章节
4、Grid 布局
Flexbox 用于设计横向或纵向的布局,而 Grid 布局被用于同时在两个维度上把元素按行和列排列整齐
(1)设置 display:grid
除了使用display:grid
,我们还分别使用 grid-template-rows
和 grid-template-columns
两个属性定义了一些行和列的轨道。定义了三个1fr
的列,还有两个100px
的行之后,无需再在子元素上指定任何规则,它们自动地排列到了我们创建的格子当中
.wrapper {display: grid;grid-template-columns: 1fr 1fr 1fr;grid-template-rows: 100px 100px;grid-gap: 10px;
}
<div class="wrapper"><div class="box1">One</div><div class="box2">Two</div><div class="box3">Three</div><div class="box4">Four</div><div class="box5">Five</div><div class="box6">Six</div>
</div>
效果如下
(2)在网格内放置元素
一旦你拥有了一个 grid,你也可以显式地将元素摆放在里面,而不是依赖于浏览器进行自动排列。在下面的第二个例子里,我们定义了一个和上面一样的 grid,但是这一次我们只有三个子元素。我们利用 grid-column
和 grid-row
两个属性来指定每一个子元素应该从哪一行/列开始,并在哪一行/列结束。这就能够让子元素在多个行/列上展开
.wrapper {display: grid;grid-template-columns: 1fr 1fr 1fr;grid-template-rows: 100px 100px;grid-gap: 10px;
}.box1 {grid-column: 2 / 4;grid-row: 1;
}.box2 {grid-column: 1;grid-row: 1 / 3;
}.box3 {grid-row: 2;grid-column: 3;
}
<div class="wrapper"><div class="box1">One</div><div class="box2">Two</div><div class="box3">Three</div>
</div>
更多信息在下面专门的 Grid网格 章节
5、浮动
把一个元素“浮动”(float) 起来,会改变该元素本身和在正常布局流(normal flow)中跟随它的其他元素的行为。这一元素会浮动到左侧或右侧,并且从正常布局流 (normal flow) 中移除,这时候其他的周围内容就会在这个被设置浮动 (float) 的元素周围环绕
float
属性有 4 个可能的值:
left
:将元素浮动到左侧right
:将元素浮动到右侧none
:默认值,不浮动inherit
:继承父元素的浮动属性
在下面这个例子当中,我们把一个<div>
元素浮动到左侧,并且给了他一个右侧的margin
,把文字推开。这给了我们文字环绕着这个<div>
元素的效果
<h1>Simple float example</h1><div class="box">Float</div><p> Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla luctus aliquam dolor, eu lacinia lorem placerat vulputate. Duis felis orci, pulvinar id metus ut, rutrum luctus orci. Cras porttitor imperdiet nunc, at ultricies tellus laoreet sit amet. Sed auctor cursus massa at porta. Integer ligula ipsum, tristique sit amet orci vel, viverra egestas ligula. Curabitur vehicula tellus neque, ac ornare ex malesuada et. In vitae convallis lacus. Aliquam erat volutpat. Suspendisse ac imperdiet turpis. Aenean finibus sollicitudin eros pharetra congue. Duis ornare egestas augue ut luctus. Proin blandit quam nec lacus varius commodo et a urna. Ut id ornare felis, eget fermentum sapien.</p>
.box {float: left;width: 150px;height: 150px;margin-right: 30px;
}
效果如下
6、定位
定位 (positioning) 能够让我们把一个元素从它原本在正常布局流 (normal flow) 中应该在的位置移动到另一个位置。定位 (positioning) 并不是一种用来给你做主要页面布局的方式,它更像是让你去管理和微调页面中的一个特殊项的位置。
有 5 种主要的定位类型需要我们了解:
- 静态定位(static positioning):元素默认属性,指放在文档布局流的默认位置
- 相对定位(relative positioning):允许我们相对于元素在正常的文档流中的位置进行移动,包括将两个元素叠放在页面上。这对于微调和精准设计非常有用
- 绝对定位(absolute positioning):将元素完全从页面的正常布局流中移除,类似将它单独放在一个图层中。我们可以将元素相对于页面的
<html>
元素边缘固定,或相对于该元素的最近被定位祖先元素。绝对定位在创建复杂布局效果时非常有用,例如通过标签显示和隐藏的内容面板或者通过按钮控制滑动到屏幕中的信息面板 - 固定定位(fixed positioning):与绝对定位类似,但它是将一个元素相对浏览器视口固定,而不是相对于另外一个元素。这在创建类似在整个页面滚动过程中总是处于屏幕的某个位置的导航菜单时非常有用
- 粘性定位(sticky positioning):一种新的定位方式,它会让元素先保持和
position: static
一样的定位,当它的相对视口位置达到某一个预设值时,它就会像position: fixed
一样定位
更多具体的在后面专门章节再仔细记录
7、表格布局
现在已经不太使用,它通常会被用于兼容一些不支持 Flexbox 和 Grid 的浏览器。
一个<table>
标签之所以能够像表格那样展示,是由于 css 默认给<table>
标签设置了一组 table 布局属性。当这些属性被应用于排列非<table>
元素时,这种用法被称为“使用 CSS 表格”
<form><p>First of all, tell us your name and age.</p><div><label for="fname">First name:</label><input type="text" id="fname"></div><div><label for="lname">Last name:</label><input type="text" id="lname"></div><div><label for="age">Age:</label><input type="text" id="age"></div>
</form>
html {font-family: sans-serif;
}form {display: table;margin: 0 auto;
}form div {display: table-row;
}form label, form input {display: table-cell;margin-bottom: 10px;
}form label {width: 200px;padding-right: 5%;text-align: right;
}form input {width: 300px;
}form p {display: table-caption;caption-side: bottom;width: 300px;color: #999;font-style: italic;
}
结果如下
8、多列布局
多列布局模组给了我们 一种把内容按列排序的方式,就像文本在报纸上排列那样。由于在 web 内容里让你的用户在一个列上通过上下滚动来阅读两篇相关的文本是一种非常低效的方式,那么把内容排列成多列可能是一种有用的技术。
要把一个块转变成多列容器 (multicol container),我们可以使用 column-count
属性来告诉浏览器我们需要多少列,也可以使用column-width
来告诉浏览器以至少某个宽度的尽可能多的列来填充容器。
<div class="container"><h1>Multi-column layout</h1><p>Paragraph 1.</p><p>Paragraph 2.</p></div>
我们指定了该容器的column-width
为 200 像素,这让浏览器创建了尽可能多的 200 像素的列来填充这一容器。接着他们共同使用剩余的空间来伸展自己的宽度
.container {column-width: 200px;}
效果如下
总结
只记录了 CSS 的部分内容