前端布局

一、Float圣杯布局&双飞翼布局

圣杯布局和双飞翼布局的出现,都是为了实现左右两侧宽度固定,中间内容宽度自适应的三栏布局,且三栏布局的特点是中间内容优先渲染显示(一般情况下重要内容都是放置在布局的中间),也就是在布局结构中,中间内容的结构位于最上面(不是传统的上下,左右结构)。两种布局方式的目的一致但是实现思路不一样,圣杯布局是由国外大佬提出来的,双飞翼布局是由淘宝内部实现的。

  • 等高布局
  • 双飞翼布局
  • 圣杯布局
  1. 等高布局
    利用margin-bottom负值与padding-bottom配合实现。

  2. 三列布局,左右固定,中间自适应

    1. BFC方式

    2. 定位

    3. 浮动 ( 双飞翼布局、圣杯布局 )
      margin负值

    4. flex弹性

二、Flex弹性盒模型

随着移动互联网的发展,对于网页布局来说要求越来越高,而传统的布局方案对于实现特殊布局非常不方便,比如垂直居中。
2009年,W3C 提出了一种新的方案----Flex 布局,可以简便、完整、响应式地实现各种页面布局。目前,它已经得到了所有浏览器的支持,这意味着,现在就能很安全地使用这项功能。

作用在flex容器上 作用在flex子项上
flex-direction order
flex-wrap flex-grow
flex-flow flex-shrink
justify-content flex-basis
align-items flex
align-content align-self

2.1 作用在flex容器上

2.1.1 flex-direction

flex-direction用来控制子项整体布局方向,是从左往右还是从右往左,是从上往下还是从下往上。

取值 含义
row 默认值,显示为行。方向为当前文档水平流方向,默认情况下是从左往右。
row-reverse 显示为行。但方向和row属性值是反的
column 显示为列
column-reverse 显示为列。但方向和column属性值是反的

2.1.2 flex-wrap

flex-wrap 用来控制子项整体单行显示还是换行显示。

取值 含义
nowrap 默认值,表示单行显示,不换行。
wrap 宽度不足换行显示
wrap-reverse 宽度不足换行显示,但是是从下往上开始,也就是原本换行在下面的子项现在跑到上面。

2.1.3 flex-flow

flex-flow属性是flex-direction和flex-wrap的缩写,表示flex布局的flow流动特性。第一个值表示方向,第二个值表示换行,中间用空格隔开。

2.1.4 justify-content

justify-content属性决定了主轴方向上子项的对齐和分布方式。

取值 含义
flex-start 默认值,表现为起始位置对齐。
flex-end 表现为结束位置对齐。
center 表现为居中对齐。
space-between 表现为两端对齐。between是中间的意思,意思是多余的空白间距只在元素中间区域分配。
space-around around是环绕的意思,意思是每个flex子项两侧都环绕互不干扰的等宽的空白间距,最终视觉上边缘两侧的空白只有中间空白宽度一半。
space-evenly evenly是匀称、平等的意思。也就是视觉上,每个flex子项两侧空白间距完全相等。

2.1.5 align-items

align-items中的items指的就是flex子项们,因此align-items指的就是flex子项们相对于flex容器在侧轴方向上的对齐方式。

设置交叉轴上的对齐方式,默认stretch,也就是拉伸

取值 含义
stretch 默认值,flex子项拉伸。
flex-start 表现为容器顶部对齐。
flex-end 表现为容器底部对齐。
center 表现为垂直居中对齐。

2.1.6 align-content

align-content可以看成和justify-content是相似且对立的属性,如果所有flex子项只有一行,则align-content属性是没有任何效果的。

如果主轴上有多行,align-content设置对齐方式

取值 含义
stretch 默认值。每一行flex子元素都等比例拉伸。例如,如果共两行flex子元素,则每一行拉伸高度是50%。
flex-start 表现为起始位置对齐。
flex-end 表现为结束位置对齐。
center 表现为居中对齐。
space-between 表现为两端对齐。
space-around 每一行元素上下都享有独立不重叠的空白空间。
space-evenly 每一行元素都完全上下等分。

2.2 作用在flex子项上的CSS属性

取值 含义
order 可以通过设置order改变某一个flex子项的排序位置。所有flex子项的默认order属性值是0。
flex-grow 属性中的grow是扩展的意思,扩展的就是flex子项所占据的宽度,扩展所侵占的空间就是除去元素外的剩余的空白间隙。默认值为0。
flex-shrink 属性中的shrink是“收缩”的意思,flex-shrink主要处理当flex容器空间不足时候,单个元素的收缩比例。默认值是1。
flex-basis flex-basis定义了在分配剩余空间之前元素的默认大小。
flex flex属性是flex-grow,flex-shrink和flex-basis的缩写。
align-self align-self指控制单独某一个flex子项的垂直对齐方式。

2.2.1 flex-basis

如果你设置了flex-basis,width就没用了。但是,max-width和 min-width 限制flex-basis。比如:

flex-basis: 100px;
width: 80px;// 最终宽度:100px
 
flex-basis: 100px;
min-width:120px;// 最终宽度:120px
 
flex-basis: 100px;
max-width: 60px;// 最终宽度:60px

2.3 Flex案例

  1. 导航步骤
  2. 两列固定,一列自适应。三列布局 ,可以加响应式
  3. 典型的手机网页布局
  4. 百度弹性导航。

三、Grid 布局

Grid 布局是CSS中最强大的布局系统。与 flexbox 的一维布局系统不同,Grid 布局是一个二维布局系统,也就意味着它可以同时处理列和行。通过将 CSS 规则应用于父元素 (网格容器)和其子元素( 网格项),你就可以轻松使用 Grid(网格) 布局。

3.1 简介

它的目标是完全改变我们基于网格的用户界面的布局方式。CSS 一直用来布局我们的网页,但一直以来都存在这样或那样的问题。一开始我们用表格(table),然后是浮动(float),再是定位(postion)和内嵌块(inline-block),但是所有这些方法遗漏了很多重要的功能(例如垂直居中)。Flexbox 的出现很大程度上改善了我们的布局方式,但它的目的是为了解决更简单的一维布局,而不是复杂的二维布局(实际上 Flexbox 和 Grid 能协同工作,而且配合得非常好)。

浏览器支持

3.2 基本概念

必须使用 display: grid 指定一个容器为网格布局,使用 grid-template-columns 和 grid-template-rows 设置 列 和 行 的尺寸大小

 .box {width:300px; height:300px; border:1px gray dotted; display: grid; 
         grid-template-rows: 100px auto 20%; 
        grid-template-columns: 100px auto 100px; 
     }
 

3.2.1 容器和项目

采用网格布局的区域,称为“容器”。容器内部的采用网格定位的子元素称为“项目”

 <div class="box">
        <div class="item"><p>1</p></div>
        <div class="item">2</div>
        <div class="item">3</div>
    </div>

上面的代码中,box就是容器,item就是项目

注意:项目只能是容器的顶层子元素,不包含项目的子元素,比如上面代码的

元素就不是项目。Grid 布局只对项目生效。

3.2.2 行和列

容器里面的水平区域称为"行"(row),垂直区域称为"列"(column)。

上图中,水平的深色区域就是"行",垂直的深色区域就是"列"。

3.2.3 单元格

行和列的交叉区域,称为"单元格"(cell)。

正常情况下,n行和m列会产生n x m个单元格。比如,3行3列会产生9个单元格。

3.2.4 网格线

划分网格的线,称为"网格线"。水平网格线划分出行,垂直网格线划分出列。

3.3 容器属性(作用在grid容器上)

Grid 布局的属性分成两类。一类定义在容器上面,称为容器属性;另一类定义在项目上面,称为项目属性。这部分先介绍容器属性。

作用在grid容器上 作用在grid子项上
grid-template-columns grid-column-start
grid-template-rows grid-column-end
grid-template-areas grid-row-start
grid-template grid-row-end
grid-column-gap grid-column
grid-row-gap grid-row
grid-gap grid-area
justify-items justify-self
align-items align-self
place-items place-self
justify-content
align-content
place-content

3.3.1 grid-template-columns 属性,grid-template-rows 属性

容器指定了网格布局以后,接着就要划分行和列。

  • grid-template-columns: 定义每一列的列宽,
  • grid-template-rows: 定义每一行的行高。

对网格进行横纵划分,形成二维布局。单位可以是像素,百分比,自适应以及fr单位(网格剩余空间比例单位)。

.container {
  display: grid;
  grid-template-columns: 100px 100px 100px;
  grid-template-rows: 100px 100px 100px;
}

上面代码指定了一个三行三列的网格,列宽和行高都是100px。

  • repeat

有时候,重复写同样的值非常麻烦,尤其网格很多时。这时,可以使用repeat()函数,简化重复的值。上面的代码用repeat()改写如下。

.container {
  display: grid;
  grid-template-columns: repeat(3, 33.33%);
  grid-template-rows: repeat(3, 33.33%);
}

repeat()接受两个参数,第一个参数是重复的次数,第二个参数是所要重复的值。

  • fr 关键字

为了方便表示比例关系,网格布局提供了fr关键字(fraction 的缩写,意为"片段")。如果两列的宽度分别为1fr和2fr,就表示后者是前者的两倍。

.container {
  display: grid;
  grid-template-columns: 1fr 1fr;
}

3.3.2 grid-template-areas 属性

网格布局允许指定"区域"(area),一个区域由单个或多个单元格组成。

grid-template-areas属性用于定义区域。

该属性必须配合子项中的grid-area来使用
grid-area:用来规定区域的名字

你可把容器当成画布,把grid-area所指定的区域当作画块

通过画块的拼接来获取想要的布局;

.container {
  display: grid;
  grid-template-columns: 100px 100px 100px;
  grid-template-rows: 100px 100px 100px;
  grid-template-areas: 'a b c'
                       'd e f'
                       'g h i';
}

上面代码先划分出9个单元格,然后将其定名为a到i的九个区域,分别对应这九个单元格。

多个单元格合并成一个区域的写法如下:

grid-template-areas: 'a a a'
                     'b b b'
                     'c c c';

上面代码将9个单元格分成a、b、c三个区域。

注意:在grid-template-areas内所指定的命名区域必须是矩形,不然浏览器不渲染

配合子项的属性 grid-area 一起使用:

.container div:nth-of-type(1) { grid-area: a1;}
.container div:nth-of-type(2) { grid-area: a2;}
.container div:nth-of-type(3) { grid-area: a3;}

3.3.3 row-gap 属性,column-gap 属性,gap 属性

  • row-gap
    设置行与行的间隔(行间距)
  • column-gap
    设置列与列的间隔(列间距)
.container {
  grid-row-gap: 20px;
  grid-column-gap: 20px;
}
  • grid-gap属性是grid-column-gap和grid-row-gap的合并简写形式,语法如下。
grid-gap: <grid-row-gap> <grid-column-gap>;

因此,上面一段 CSS 代码等同于下面的代码。

.container {
  grid-gap: 20px 20px;
}

根据最新标准,上面三个属性名的grid-前缀已经删除,grid-column-gap和grid-row-gap写成column-gap和row-gap,grid-gap写成gap。

3.3.4 justify-items 属性,align-items 属性,place-items 属性

  • justify-items
    设置单元格内容的水平位置(左中右)
  • align-items
    设置单元格内容的垂直位置(上中下)
.container {
  justify-items: start | end | center | stretch;
  align-items: start | end | center | stretch;
}

这两个属性的写法完全相同,都可以取下面这些值。

取值 含义
stretch 默认值,拉伸。表现为水平或垂直填充。
start 表现为容器左侧或顶部对齐。
end 表现为容器右侧或底部对齐。
center 表现为水平或垂直居中对齐。

place-items可以让align-items和justify-items属性写在单个声明中。

place-content: align-content(垂直)   justify-content(水平);

3.3.5 justify-content和align-content

  • justify-content
    整个内容区域在容器里面的水平位置(左中右)
  • align-content
    整个内容区域的垂直位置(上中下)
取值 含义
stretch 默认值,拉伸。表现为水平或垂直填充。
start 表现为容器左侧或顶部对齐。
end 表现为容器右侧或底部对齐。
center 表现为水平或垂直居中对齐。
space-between 表现为两端对齐。
space-around 享有独立不重叠的空白空间。
space-evenly 平均分配空白空间

place-content:align-content和justify-content属性的缩写

place-content: <align-content(垂直) >  <justify-content(水平)>;

3.4 作用在grid子项上的CSS属性

取值 含义
grid-column-start 水平方向上占据的起始位置。
grid-column-end 水平方向上占据的结束位置。(span属性)
grid-row-start 垂直方向上占据的起始位置。
grid-row-end 垂直方向上占据的结束位置。(span属性)
grid-column grid-column-start + grid-column-end的缩写。
grid-row grid-row-start + grid-row-end的缩写。
grid-area 表示当前网格所占用的区域,名字和位置两种表示方法。
justify-self 单个网格元素的水平对齐方式。
align-self 单个网格元素的垂直对齐方式。
place-self align-self和justify-self的缩写。

span && [ ]

为网格项的放置提供网格跨度,这样网格项的网格区域的行结束边缘是从起始边缘开始的n行

缩写:grid-row:行开始 行结束

grid-column :列开始 列结束

3.4.1 grid-area

grid-area属性在网格布局中指定网格项的大小和位置,并且是以下属性的简写属性:

  • grid-row-start
    指定开始显示项目的行。
  • grid-column-start
    开始显示项目的列
  • grid-row-end
    停止显示项目的行线或要跨越的行数
  • grid-column-end
    指定停止显示项目的列线,或跨越的列数

grid-area属性还可用于为网格项指定名称。然后,可以通过网格容器的grid-template-areas属性引用命名网格项 。

CSS语法

grid-area: grid-row-start / grid-column-start / grid-row-end / grid-column-end | itemname;
 
grid-area: 行开始 列开始 行结束 列结束

第几行 几列 开始 到几行 几列结束

实例

使“item1”从第2行第1列开始,并跨越2行3列:

.item1 {
 grid-area: 2 / 1 / span 2 / span 3;
}

3.5 Grid案例

  1. 骰子的点数。
  2. 百度搜索风云榜。

案例1.png

四、移动端布局

国内的UC和QQ,百度等手机浏览器都是根据Webkit修改过来的内核,国内尚无自主研发的内核,就像国内的手机操作系统都是基于Android修改开发的一样。

总结:兼容移动端主流浏览器,处理Webkit内核浏览器即可。

4.1 手机屏幕的现状

  • 移动端设备屏幕尺寸非常多,碎片化严重。
  • Android设备有多种分辨率:480x800, 480x854, 540x960, 720x1280,1080x1920等,还有传说中的2K,4k屏。
  • 近年来iPhone的碎片化也加剧了,其设备的主要分辨率有:640x960, 640x1136, 750x1334, 1242x2208等。
  • 作为开发者无需关注这些分辨率,因为我们常用的尺寸单位是 px 。

4.2 常见移动端屏幕尺寸

设备像素(device pixel):

设备像素又称 物理像素 ,是设备能控制显示的最小单位,我们可以把它看做显示器上的一个点。我们常说的 1920x1080像素分辨率就是用的设备像素单位
也就是平时所说的分辨率,比如 iphone6s 的分辨率是 750*1334

设备像素是物理概念,指的是设备屏幕上的像素点个数,比如iPhone 5的分辨率640 x 1136px,那么水平方向上有640个像素点,竖直方向上有1136个像素点。

设备独立像素:

一台设备上程序用来描绘数据的一个个的“点”,也就是虚拟的像素。以前设备像素对应一个设备独立像素,后来出现了高分辨率的手机,不可能再一个设备像素对应一个设备独立像素了,因为这样东西会被缩小,看不清。(想象一下两台尺寸相同的手机,A的分辨率是B的三倍,那么同一张图片在A上的面积 = B上的面积 / 9。)

所以一般高像素设备都是多个设备像素显示一个设备独立像素。

可以在浏览器控制台输出 screen.width , screen.height查看设备独立像素。

设备像素比(DPR)

设备像素/设备独立像素,(手机宽设备像素/手机宽设备独立像素)设备像素比越高渲染越精致。

也就是一个虚拟像素对应多少个物理像素, 比如,iphone6s 的分辨率是 750*1334,设备独立像素是 375 * 667,那么它的设备像素比就是 750 / 375 = 2

设备像素比(DPR) = 设备像素/设备独立像素

可以在浏览器控制台输出window.devicePixelRatio查看设备像素比。

在css中,可以通过-webkit-device-pixel-ratio,-webkit-min-device-pixel-ratio和-webkit-max-device-pixel-ratio进行媒体查询,对不同dpr的设备,做一些样式适配(这里只针对webkit内核的浏览器和webview)。

CSS像素(css pixel):

css像素是 web编程的概念 ,它是抽象的 ,实际上不存在 。用于逻辑上衡量像素的单位。也就是我们做网页时用到的css像素单位。

写CSS的时候我们所用的像素px。应该说在PC端CSS像素就是设备独立像素,但移动端就不一定了。

屏幕尺寸

屏幕对角线的长度,以英尺为单位

像素密度(PPI)

每英寸屏幕拥有的像素数,PPI的值越高,画质越好,看起来更有逼格。

我们不妨用上面的公式做做数学题,见下图:

下面我们来计算一下 iphone6 plus 的ppi;

var ppi = sqrt(1920X1920+1080X1080)/5.5; 计算结果ppi 为 400.528576,实际上会有出入,但这没关系。

注:
键盘上面按下【Windows + R】组合键,调出“运行”窗口
在“运行”窗口里边输入“calc”,再按回车键。

4.2 设备像素和独立设备像素的关系(实例)

以iphone6 为例:

设备宽高为375×667,可以理解为设备独立像素(或css像素),眼睛能看到的尺寸。
物理像素比(dpr)为2,根据上面的计算公式,其物理像素(设备像素)就应该×2,为750×1334。

上图中可以看出,对于这样的css样式:

width: 2px;
height: 2px;

在不同的屏幕上(普通屏幕 vs retina屏幕),css像素所呈现的大小(物理尺寸)是一致的,不同的是1个css像素所对应的物理像素(设备像素)个数是不一致的。
在普通屏幕下,1个css像素 对应 1个物理像素(1:1)。 在retina 屏幕下,1个css像素对应 4个物理像素(1:4)。

在CSS规范中,长度单位可以分为两类,绝对单位以及相对单位。

px是一个相对单位,相对的是设备像素(device pixel)。 设备像素==物理像素

4.3 移动端调试方法

  • Chrome DevTools(谷歌浏览器)的模拟手机调试
  • 搭建本地web服务器,手机和服务器一个局域网内,通过手机访问服务器
  • 使用外网服务器,直接IP或域名访问

4.4 视口

视口(viewport)就是浏览器显示页面内容的屏幕区域。 视口可以分为layout viewport(布局视口)、 visual viewport(可视视口)和理想视口

4.4.1 布局视口 layout viewport

一般移动设备的浏览器都默认设置了一个布局视口,用于解决早期的PC端页面在手机上显示的问题。

iOS, Android基本都将这个视口分辨率设置为 980px,所以PC上的网页大多都能在手机上呈现,只不过元素看上去很小,一般默认可以通过手动缩放网页。

layout viewport 可改变大小,在下面。Layout viewport默认大小为980像素,可通过document.documentElement.clientWidth获取。

4.4.2 视觉视口 visual viewport

字面意思,它是用户正在看到的网站的区域。注意:是网站的区域。

我们可以通过缩放去操作视觉视口,但不会影响布局视口,布局视口仍保持原来的宽度。

4.4.3 理想视口 ideal viewport

为了使网站在移动端有最理想的浏览和阅读宽度而设定

理想视口,对设备来讲,是最理想的视口尺寸

需要手动添写meta视口标签通知浏览器操作

meta视口标签的主要目的:布局视口的宽度应该与理想视口的宽度一致,简单理解就是设备有多宽,我们布局的视口就多宽

总结:我们开发最终会用理想视口,而理想视口就是将布局视口的宽度修改为视觉视口

4.4.4 meta标签

通过 <meta>标签进行设置,name属性指定viewport值,content属性进行视口配置。

取值 含义
width 设置layout viewport的宽度特定值,device-width表示设备宽。
height 设置layout viewport的高度特定值,一般不进行设置。
initial-scale 设置页面的初始缩放。
minimum-scale 设置页面的最小缩放。
maximum-scale 设置页面的最大缩放。
user-scalable 设置页面能否进行缩放。

最标准的viewport设置

  • 视口宽度和设备保持一致
  • 视口的默认缩放比例1.0
  • 不允许用户自行缩放
  • 最大允许的缩放比例1.0
  • 最小允许的缩放比例1.0

现代网页需要将layout viewport设置成跟visual viewport等同大小,方便进行网页制作。

<meta name="viewport" content="width=device-width, initial-scale=1.0">

  /* @media媒体查询的写法 */
        /* all : 用于所有设备 */
        /* and () 条件查询的拼接  */
        /* (min-width:500px)  最小宽度是 500px, 也就是说宽度大于500px的时候有效 */

4.5 移动开发选择和技术解决方案

1. 移动端主流方案

单独制作移动端页面(主流),pc和mobile各一套

通常情况下,网址域名前面加 m(mobile) 可以打开移动端。通过判断设备,如果是移动设备打开,则跳到移动端页面。

也就是说,PC端和移动端为两套网站,pc端是pc断的样式,移动端在写一套,专门针对移动端适配的一套网站

2. 响应式页面兼容移动端(其次)

响应式网站:即pc和移动端共用一套网站,只不过在不同屏幕下,样式会自动适配

4.6 移动端技术解决方案

移动端浏览器兼容问题

移动端浏览器基本以 webkit 内核为主,因此我们就考虑webkit兼容性问题。

我们可以放心使用 H5 标签和 CSS3 样式。

同时我们浏览器的私有前缀我们只需要考虑添加 webkit 即可

4.7 移动端大量使用 CSS3盒子模型box-sizing

  • 传统模式宽度计算:盒子的宽度 = CSS中设置的width + border + padding
  • CSS3盒子模型: 盒子的宽度= CSS中设置的宽度width 里面包含了 border 和 padding

也就是说,我们的CSS3中的盒子模型, padding 和 border 不会撑大盒子了

/\*CSS3盒子模型\*/  
box-sizing: border-box;  
/\*传统盒子模型\*/  
box-sizing: content-box;  

移动端可以全部CSS3 盒子模型

PC端如果完全需要兼容,我们就用传统模式,如果不考虑兼容性,我们就选择 CSS3 盒子模型

4.8 移动端特殊样式

 /*CSS3盒子模型*/  
 box-sizing: border-box;  
 /*点击高亮需要清除,  设置为transparent 完成透明*/  
 -webkit-tap-highlight-color: transparent;  
 /*在移动端浏览器默认的外观在iOS上加上这个属性才能给按钮和输入框自定义样式*/  
 -webkit-appearance: none;  
 /*禁用长按页面时的弹出菜单*/  
 img,a { -webkit-touch-callout: none; }  

-webkit-tap-highlight-color

这个属性只用于iOS (iPhone和iPad)。当你点击一个链接或者通过Javascript定义的可点击元素的时候,它就会出现一个半透明的灰色背景。要重设这个表现,你可以设置-webkit-tap-highlight-color为任何颜色。
想要禁用这个高亮,设置颜色的alpha值为0即可。

浏览器支持: 只有iOS(iPhone和iPad).

示例:设置高亮色为50%透明的红色:
-webkit-tap-highlight-color: rgba(255,0,0,0.5);

webkit-appearance
-webkit-appearance: none;
//消除输入框和按钮的原生外观,在iOS上加上这个属性才能给按钮和输入框自定义样式 。
注意:不同type的input使用这个属性之后表现不一。text、button无样式,radio、checkbox直接消失

-webkit-user-select
-webkit-user-select: none;
// 禁止页面文字选择 ,此属性不继承,一般加在body上规定整个body的文字都不会自动调整

4.9 移动端常见布局

  • 移动端单独制作

    • 流式布局(百分比布局)
    • flex 弹性布局(强烈推荐)
    • rem+媒体查询布局
    • 混合布局
  • 响应式

    • 媒体查询
    • bootstarp

4.9.1 流式布局(百分比布局)

流式布局,就是百分比布局,也称非固定像素布局。
通过盒子的宽度设置成百分比来根据屏幕的宽度来进行伸缩,不受固定像素的限制,内容向两侧填充。
流式布局方式是移动web开发使用的比较常见的布局方式。

流式布局,就是百分比布局,也称为非固定像素布局


好处: 大屏幕下显示更多的内容。 坏处:宽屏下比例会有一些不协调。

4.9.2 flex 弹性布局(强烈推荐)

4.9.3 rem+媒体查询布局

单位:
em : 是一个相对单位,1em等于当前元素或父元素的font-size值。
rem : 是一个相对单位,1rem等于根元素的font-size值。
vw / vh : 把屏幕分为100份,1vw等于屏幕宽的1%。

rem和em很容易混淆,其实两个都是css的单位,并且也都是相对单位,先有的em,css3才引入的rem,在介绍rem之前,我们先来了解下em:

em可以让我们的页面更灵活,更健壮,比起到处写死的px值,em似乎更有张力,改动父元素的字体大小,子元素会等比例变化

这一变化似乎预示了无限可能,有些人提出用em来做弹性布局页面,em做弹性布局的缺点还在于牵一发而动全身,一旦某个节点的字体大小发生变化,那么其后代元素都得重新计算,X﹏X

  • rem作用于非根元素时,相对于根元素字体大小;
  • rem作用于根元素字体大小时,相对于其出初始字体大小——MDN

rem取值分为两种情况,设置在根元素时和非根元素时,举个例子:

/* 作用于根元素,相对于原始大小(16px),所以html的font-size为32px*/
html{font-size:2rem}
/* 作用于非根元素,相对于根元素字体大小,所以为64px */
p{font-size:2rem}

em有rem的优点,em有em的优点,尺有所短,寸有所长
选择合适的技术,并让其发挥优势

我一直觉得em就是为字体和行高而生的,有些时候子元素字体就应该相对于父元素,元素行高就应该相对于字体大小;而rem的有点在于统一的参考系

Rem布局原理

其实rem布局的本质是等比缩放,一般是基于宽度

假设我们将屏幕宽度平均分成100份,每一份的宽度用x表示,x = 屏幕宽度 / 100,如果将x作为单位,x前面的数值就代表屏幕宽度的百分比

p{width:50x}/* 屏幕宽度的50% */

如果想要页面元素随着屏幕宽度等比变化,我们需要上面的x单位,不幸的是css中并没有这样的单位,幸运的是在css中有rem,通过rem这个桥梁,可以实现神奇的x
通过上面对rem的介绍,可以发现,如果子元素设置rem单位的属性,通过更改html元素的字体大小,就可以让子元素实际大小发生变化

/* 作用于根元素,相对于原始大小(16px),所以html的font-size为32px*/
html{font-size:2rem}
/* 作用于非根元素,相对于根元素字体大小,所以为64px */
p{font-size:2rem}

如果让html元素字体的大小,恒等于屏幕宽度的1/100,那1rem和1x就等价了

html{fons-size:width/100}
p{width:50rem}
/* 50rem = 50x = 屏幕宽度的50% */
  • 动态设置font-size:

  • 通过JS

  • 通过vw

注:要给body重置一下font-size : 16px

六. 去访问一些网站的PC端和移动端?

大一点的网站都是分开开发的,PC端一套代码,移动端端一套代码。

访问淘宝网 -> 后端检测当前设备 -> 如果是PC端 -> www.taobao.com

访问淘宝网 -> 后端检测当前设备 -> 如果是移动端 -> www.taobao.com重定向 -> h5.m.taobao.com

参考:

 
https://www.jianshu.com/p/99afcb3893ca
 
https://segmentfault.com/a/1190000015884091
 
posted @ 2022-03-05 16:53  Hello霖  阅读(102)  评论(0编辑  收藏  举报