常规流(Normal Flow)
-
根元素、浮动和绝对定位的元素会脱离常规流
-
其它元素都在常规流之内(in-flow)
-
常规流中的盒子,在某种排版上下文中参与布局
行级排版上下文 Inline Formatting Context (IFC)
-
只包含行级盒子的容器会创建一个IFC
-
IFC 内的排版规则
- 盒子在一行内水平摆放
- 一行放不下时,换行显示
- text-align 决定一行内盒子的水平对齐
- vertical-align 决定一个盒子在行内的垂直对齐
- 避开浮动(float)元素*
<div>
This is a paragraph of text with long word Honorificabilitudinitatibus. Here is an image
<img src="https://assets.codepen.io/59477/cat.png" alt="cat">
And <em>Inline Block</em>
</div>
<style>
div {
width: 10em;
//overflow-wrap: break-word;
background: #411;
}
em {
display: inline-block;
width: 3em;
background: #33c;
}
</style>
<div> 本身是一个块级元素,但<div> 里面都是行级元素——只包含行级盒子的容器会创建一个行级排版上下文,因此,<div>创建了一个行级排版上下文。
display: inline-block 让 <em> 成为一个整体,不会被分割成多行。
Honorificabilitudinitatibus 是一个整体,不会被拆分,就会超出 <div> 设置的宽度。
可以使用 overflow-wrap: break-word,当单词超出容器时,会被强制换行。
块级排版上下文 Block Formatting Context (BFC)
-
某些容器会创建一个BFC
- 根元素
- 浮动、绝对定位、inline-block
- Flex子项和Grid子项
- overflow 值不是 visible 的块盒
- display: flow-root;
-
BFC 内的排版规则
- 盒子从上到下摆放
- 垂直 margin 合并
- BFC 内盒子的 margin 不会与外面的合并
- BFC 不会和浮动元素重叠
常规流里一个盒子内的子级盒子,只能都是块级,或者都是行级。如果都是块级,就从上到下排列;如果都是行级,就从左到右排列。
<span>
This is a text and
<div>block</div>
and other text.
</span>
<style>
span {
line-height: 3;
border: 2px solid red;
background: coral;
}
div {
line-height: 1.5;
background: lime;
}
</style>
<span>本身是一个行盒,但盒子内又有行盒,又有块盒,此时浏览器会产生一个匿名的块级盒子(只能在 CSS 排版引擎中看到)来包裹橙色的两段文字。
Flex Box
Flex Box 是什么
-
一种新的排版上下文
-
它可以控制子级盒子的:
- 摆放的流向 ( → ← ↑ ↓ )
- 摆放顺序
- 盒子宽度和高度
- 水平和垂直方向的对齐
- 是否允许折行
<div class="container">
<div class="a">A</div>
<div class="b">B</div>
<div class="c">C</div>
</div>
<style>
.container {
display: flex;
border: 2px solid #966;
}
.a, .b, .c {
text-align: center;
padding: 1em;
}
.a {
background: #fcc;
}
.b {
background: #cfc;
}
.c {
background: #ccf;
}
</style>
display: flex:子盒都遵循flex排版上下文的规则。
flex-direction
默认是从左到右。
对齐
主轴方向的对齐:justify-content
默认是 flex-start
- space-between —— 两端对齐,中间间隔相等,两侧没空格
- space-around —— 整行分散,两侧空格小,中间空格大
- space-evenly —— 整行分散,两侧空格与中间空格大小相等
侧轴方向的对齐:align-items
- stretch —— 将容器内元素高度撑到与容器一样高
- baseline —— 基线对齐,容器内所有子元素的基线对齐
align-items 属性设置在容器上,针对某个特定子元素设置对齐使用 align-self
按序对齐方式 order:给元素设置不同的数字 ,然后按着数字大小 从小到大 排序。
Flexibility
-
可以设置子项的弹性:当容器有剩余空间时,会伸展;容器空间不够时,会收缩。
-
flex-grow 有剩余空间时的伸展能力
-
flex-shrink 容器空间不足时收缩的能力
-
flex-basis 没有伸展或收缩时的基础长度(默认为设置的
width大小,一般不设置flex-basis) -
flex-grow
<div class="container">
<div class="a">A</div>
<div class="b">B</div>
<div class="c">C</div>
</div>
<style>
.container {
display: flex;
}
.a, .b, .c {
width: 100px;
}
.a {
flex-grow: 2;
}
.b {
flex-grow: 1;
}
</style>
整个容器减去原先没拉伸时的大小(即300px),剩下的容器空间按照 2 :1 ,分配给 A 和 B。并非指 A :B 是 2 :1。
.a, .b, .c {
width: 400px;
}
.a {
flex-shrink: 0;
}
</style>
整个容器无法含下三个元素共1200px,A 不进行压缩,B、C根据剩下的容器空间一分为二
flex-grow、flex-shrink、flex-basis可以缩写为flex 属性
Grid 布局
Grid 布局是二维的布局方式
display:grid
划分网格 grid-template
grid-template-columns: 100px 100px 200px;
grid-template-rows: 100px 100px
三列两行:列宽分别为 100px,100px,200px;行高均为 100px。
grid-template-columns: 30% 30% auto;
grid-template-rows: 100px auto
auto:自动充满
三列两行:列宽分别为30%,30%,40%;行高分别为 100 px,高度-100px。
grid-template-columns: 100px 1fr 1fr;
grid-template-rows: 100px 1fr
fr:fraction,表示一份
三列两行;第一列列宽为 100px,剩下的宽度第二列、第三列各占一份;第一行高度为 100px,剩下的高度第二行占一份。
网格线 grid line:
网格区域 grid area:
.a {
grid-row-start: 1;
grid-column-start: 1;
grid-row-end: 3;
grid-column-end: 3;
}
也可以写成
.a {
grid-area: 1/1/3/3;
}
浮动(Float)
用于实现文字环绕效果。
<section>
<img src="https://p4.ssl.qhimg.com/t017aec0e7edc961740.jpg" width="300" alt="mojave" />
<p>莫哈韦沙漠不仅纬度较高,而且温度要稍微低些,是命名该公园的短叶丝兰——约书亚树的特殊栖息地。约书亚树以从茂密的森林到远远间隔的实例等各种形式出现。除了约书亚树森林之外,该公园的西部包括加州沙漠里发现的最有趣的地质外观。
</p>
</section>
<style>
img {
float: left;
}
p {
font-size: 20px;
line-height: 1.8;
}
</style>
定位(Position)
position 属性
-
static:默认值,非定位元素(静态的,参与流常规流中的布局)
-
relative:相对自身原本位置偏移,不脱离文档流(原先空间依旧被占有,对其它元素没有影响)
-
absolute:绝对定位,相对非 static 祖先元素定位 (整个容器不会预留原先的空间,其他元素当作它不存在进行排版)
-
fixed:相对于视口绝对定位(脱离了常规的文档流)
<h1>页面标题</h1>
<div class="container">
<div class="box"></div>
<p>段落内容段落内容 1</p>
<p>段落内容段落内容 2</p>
<p>段落内容段落内容 3</p>
<p>段落内容段落内容 4</p>
</div>
<style>
.container {
background: lightblue;
}
.box {
position: absolute;
top: 0;
left: 0;
width: 100px;
height: 100px;
background: red;
}
</style>
container 、<body>都是 static 的定位(未设置即默认 static),因此 box 根据页面的边缘进行定位。
<nav>
<a href="#">首页</a>
<a href="#">导航1</a>
<a href="#">导航2</a>
</nav>
<main>
<section>1</section>
<section>2</section>
<section>3</section>
<section>4</section>
<section>5</section>
</main>
<a href="#" class="go-top">返回顶部</a>
<style>
nav {
position: fixed;
line-height: 3;
background: rgba(0, 0, 0, 0.3);
width: 100%;
}
.go-top {
position: fixed;
right: 1em;
bottom: 1em;
color: #fff;
}
nav a {
padding: 0 1em;
color: rgba(255, 255, 255, 0.7);
}
nav a:hover {
color: #fff;
}
body {
margin: 0;
font-size: 14px;
}
a {
color: #fff;
text-decoration: none;
}
section {
height: 22vh;
color: #fff;
text-align: center;
font-size: 5em;
line-height: 22vh;
}
section:nth-child(1) {
background: #F44336;
}
section:nth-child(2) {
background: #3F51B5;
}
section:nth-child(3) {
background: #FFC107;
}
section:nth-child(4) {
background: #607D8B;
}
section:nth-child(5) {
background: #4CAF50;
}
</style>
页面滚动,导航栏 <nav> 和 返回顶部 go-top相对页面是固定的。
学习建议
- 充分利用 MDN 和 M3C CSS 规范
- 保持好奇心,善用浏览器的开发者工具
- 持续学习, CSS 新特性还在不断出现
学习心得:
常规流是页面中大多数元素的默认排版方式,而浮动和绝对定位则可以用于特殊的布局需求,比如文字环绕和图层叠放。Flex Box和Grid布局可以灵活地定义子元素在行和列中的排列方式,使页面布局更加简洁和灵活。在实际开发中,灵活运用常规流、浮动、绝对定位、Flex Box和Grid布局,可以提升用户体验和交互效果。