# e-css
**Repository Path**: ymcdhr/e-css
## Basic Information
- **Project Name**: e-css
- **Description**: bfc、ifc、盒子模型、三栏布局、画三角形、flex、rem响应式布局等特性
- **Primary Language**: Unknown
- **License**: Not specified
- **Default Branch**: master
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 0
- **Forks**: 0
- **Created**: 2021-08-17
- **Last Updated**: 2021-11-09
## Categories & Tags
**Categories**: Uncategorized
**Tags**: None
## README
# CSS【持续更新】
## BFC 考点:
希望大家可以了解 BFC 是什么,以及如何形成,如何解决生产环境里的实际问题。该题目的的表述思路,我提供一篇文章的思路。
文章地址:https://zhuanlan.zhihu.com/p/111106266?utm_source=wechat_session&utm_medium=social&utm_oi=984784516690464768&s_r=0
### BFC 块级格式化上下文
### BFC 的作用:(这块其实就是在阐述在实际工作里的应用场景)
- 清除浮动
- 清除外边距折叠(父元素与子元素的 margin 折叠,子元素之间还不全能清除)
- 左图右文布局
### BFC 如何产生 (代码层面 BFC 是如何产生的)
- **根元素** :html 根元素本身就是一个 BFC 元素记住就好,body 元素不是?!【body待确认】
- **浮动元素** :float 除 none 以外的值
- **绝对定位** :position 属性为 absolute 或 fixed
- **常用行内块元素** :display 属性为 inline-block、table-cells、flex、grid 或 inline-grid 元素
- **overflow 除了 visible 以外的值** (hidden、auto、scroll)
### BFC 原理
1. 三种文档定位方式:
- 普通流
- 浮动
- 绝对定位
2. 具体产生原因:
BFC 是上面三种布局方式中的普通流, **BFC 会产生一个独立的容器,该容器内部的元素不会在布局上- 影响到外部的元素,在外部的普通流看来它和其他普通流元素无差别,文档最终会按照上面说的普通流计算布局** 。
#### margin 外边距折叠:
1. 现象:
- (1) 子元素与父元素之间的 margin 发生了折叠;
- (2) 上下两个子元素之间的 maigin 也发生了折叠,取最大值;

```html
Document
```
2. 解决外边距折叠的方法:
- 父子元素之间的折叠:给父元素创建 BFC(经测试:float、inline-block、absolute、overflow 等 BFC 都行)
- 上下两个子元素之间的:给子元素添加 float、inline-block 等样式就不会和垂直方向上其他元素的 margin 折叠(经测试:float、inline-block 可行、overflow 不行,absolute 绝对定位其实没啥意义因为本身就是绝对定位了)

```
Document
```
## IFC 规范
在行内格式化上下文中,框(boxes)一个接一个地水平排列,起点是包含块的顶部。水平方向上的 margin,border 和 padding在框之间得到保留。框在垂直方向上可以以不同的方式对齐:它们的顶部或底部对齐,或根据其中文字的基线对齐。包含那些框的长方形区域,会形成一行,叫做行框。
#### IFC 形成条件
- 块级元素中仅包含内联级别元素
- 形成条件非常简单,需要注意的是当IFC中有块级元素插入时,会产生两个匿名块将父元素分割开来,产生两个IFC,这里不做过多介绍。
#### IFC 规则
- **【排列】** 子元素 **水平方向横向排列** ,并且垂直方向起点为元素顶部。
- **【样式】** 子元素 **只会计算横向样式空间** ,【padding、border、margin】,垂直方向样式空间不会被计算,【padding、border、margin】(不可替换内联子元素只有横向空间可计算,可替换的还是有效)。
- **【对齐】** 在垂直方向上,子元素会以不同形式来 **垂直对齐(vertical-align)**
- **【宽度】** 能把在一行上的框都完全包含进去的一个矩形区域,被称为该行的行框(line box)。 **行框的宽度** 是由包含块(containing box)和与其中的浮动来决定。
- **【排列】** IFC中的行框一般左右边贴紧其包含块,但float元素会优先排列。
- **【高度】** IFC中的 **行框高度** 由 CSS 行高计算规则来确定,同个IFC下的多个line box高度可能会不同。
- **【对齐】** 当内联元素的总宽度少于包含它们的行框宽度时,其 **水平对齐** 由 text-align 属性值来决定。
- **【换行】** 当行框里面的所有元素超过父元素的宽度时,它会被分割成多个boxes,这些 boxes 分布在多个“line box”中。如果子元素未设置强制换行的情况下,“inline box”将不可被分割,将会溢出父元素。
#### IFC 应用实例

1. 只会计算横向样式空间,注意这里是针对 IFC 里面的不可替换内联元素,如:a、span 等;(可替换元素如:input、img 还是有效的)
2. 内联元素的居中对齐,如下示例中:父元素设置 text-align:center
3. float 元素会优先排列,注意示例中的 float 元素在最左边;
```
Document
```
## CSS 实现三角形或者梯形
```
.box{
width:50px;
height:50px;
background-color:blue;
border-top:50px solid red;
border-right:50px solid yellow;
border-bottom:50px solid green;
border-left:50px solid pink;
}
```

## 盒子模型(box-sizing)

```html
Document
```
## css优先级如何计算
- !important => 内联 => id => class => tag
- !important 比 内联优先级高,class同级情况下根据class数量叠加计算,还是同级的情况下,写在后面的会覆盖前面的。
## 伪类和伪元素
#### 伪类和伪元素的区别
伪类和伪元素的根本区别在于:它们是否创造了新的元素。
#### 伪类
:hover、:visited、:active、:first-child 等,本质上还是选择器;

#### 伪元素
::before、::after、::placeholder 会创造一个新的元素,可以设置其样式;部分伪元素可以使用一个冒号。

## 1像素边框
#### 存在问题
1. 由于现在的移动设备通常 dpr 都是 2、3,所以 1px 的边框相对显示会更粗;
2. 当前苏宁和淘宝基本还是最小调用的 1px

#### 如何在高 dpr 上显示小于 1px 的边框
1. **方案1:** 根据 dpr 做适配
- **方案:** 使用 css 媒体查询区分dpr:-webkit-min-device-pixel-ratio,通过dpr来区分使用不同分辨率的图片
- **问题:** 存在兼容性问题, **ios8+ 支持,经测试 Android10+ 支持** ;淘宝应该是固定使用 2 倍于 css 像素的图片,并未使用媒体查询区分 dpr。
```html
Document
```
2. **方案2:border-image**

3. **方案3:** 使用0.5px
- **问题:** 目前测试 ios 支持,chrome 不支持,经测试 Android10+ 支持
4. **方案4:** 使用 Transform
```css
.border{
width: 100%;
height: 100px;
border: 1px solid cornflowerblue;
box-sizing: border-box;
transform: scale(0.5);
-webkit-transform: scale(0.5);
}
```
## 图片的适配
#### 物理像素
#### css像素
#### dpr
**1. 苹果;** dpr 通常使用 2 来适配(taobao 是使用 2 倍于 css 像素的图片)
- iphone6/7/8:dpr为2
- iphone6/7/8 Plus、iphone X/XS/11:dpr为3
**2. 安卓;** dpr 通常使用 2 来适配;
- 安卓:dpr为1.5、2、3
**3. 适配方案:**
- **方案:** 使用 css 媒体查询区分dpr:-webkit-min-device-pixel-ratio,通过dpr来区分使用不同分辨率的图片
- **问题:** 存在兼容性问题, **ios8+支持,android支持与否不详** ;淘宝应该是固定使用 2 倍于 css 像素的图片,并未使用媒体查询区分 dpr。
```html
Document
```
## Meta ViewPort
- 淘宝
```
```
- 苏宁
```
```
#### Meta ViewPort 禁止移动端上缩放的功能:
1. 首先,需要禁止缩放的原因,参考:https://www.zhihu.com/question/20372355
- 移动浏览器上双指缩放的本意,是让为桌面设计的页面可以在手机上(一定程度上)正常显示。因为最初互联网上并没有专门为移动设备设计的网页,大多数页面的宽度都是在 960+px,如果直接拿到手机设备上显示的话,一种情况是适应宽度,但是网页会被缩得太小,看不清楚字。另一种情况是采用网页的实际大小,但是会导致页面显示不全。移动浏览器很难去判断最佳的缩放倍数,所以他们实现了一个双指缩放的功能,让用户自己来选择。
- 现在很多基于 HTML5 的 Web App 已经为移动设备做过优化,所以页面缩放的功能也就不再必要了。反而当 Web App 需要实现多指触摸的时候,浏览器原生提供的缩放功能成为了一种阻碍
- 另外,大多数移动浏览器上都有缩放字体的功能,老花眼或近视眼的同学可以使用那个功能
2. 禁止缩放实现方案以及原理:
- initial-scale=1.0:强制让文档的宽度与设备的宽度保持1:1
- maximum-scale=1.0:文档最大的宽度比例是1.0
- user-scalable=0:且不允许用户点击屏幕放大浏览;
- 尤其要注意的是:content里多个属性的设置一定要用“分号+空格”来隔开,如果不规范将不会起作用。
- (1)
- (2)
- (3)
- (4)
3. 参数说明:
- width – viewport的宽度
- height – viewport的高度
- initial-scale – 初始的缩放比例
- minimum-scale – 允许用户缩放到的最小比例
- maximum-scale – 允许用户缩放到的最大比例
- user-scalable – 用户是否可以手动缩放
- viewport-fit - 针对iphone刘海屏,占满屏幕;设置了这个属性后,页面就会填充整个刘海区域(前提是浏览器或套页面的app必须做了iphonex的兼容)。
- 第二个meta标签是iphone设备中的safari私有meta标签,它表示:允许全屏模式浏览;
- 第三个meta标签也是iphone的私有标签,它指定的iphone中safari顶端的状态条的样式;
- 第四个meta标签表示:告诉设备忽略将页面中的数字识别为电话号码
4. 在设置了initial-scale=1之后,我们终于可以以1:1的比例进行页面设计了。
5. 关于viewport,还有一个很重要的概念是:iphone 的safari 浏览器完全没有滚动条,而且不是简单的“隐藏滚动条”,是根本没有这个功能。iphone 的safari 浏览器实际上从一开始就完整显示了这个网页,然后用viewport 查看其中的一部分。当你用手指拖动时,其实拖的不是页面,而是viewport。浏览器行为的改变不止是滚动条,交互事件也跟普通桌面不一样。(请参考:指尖的下JS系列文章)
## CSS实现三栏布局【遗留问题,还有不更好的方案?】
#### float + BFC 方案,适合两边固定中间伸缩【利用BFC?】
- 左右div设置为float。
- 中间div设置为block且需要放到最后的位置,左右float形成的bfc导致文件被夹在中间【问题是为什么中间的div要放到最后?】。

```html
Document
```
- 如果中间的div不放在最后,会是如下效果(可能和ifc有关,右边的一列在文字后面会换行,然后float移到右边):

#### float 方案 + rem+ vw/vh,适合商品列表展示

```html
Document
```
#### flex + rem,适合商品列表展示


#### box + rem,适合商品列表展示(可被flex取代)
## css 实现弹出层居中 + 动画效果
1. 示例效果

2. 动画定义
- 先定义关键帧 keyframes,从一个状态到另一个状态的样式;
- 在定义动画执行 animation,执行时长以及执行方式;
```html
Document
```
## z-index 7层层叠
https://blog.csdn.net/runner_123/article/details/83309912
#### z-index 使用规则
1. z-index 必须在定位元素上才有效:relative/absolute/fixed/sticky
2. z-index 可以有负值
3. 不同父元素的子元素之间进行显示时,会根据父级元素的z-index进行渲染(如图)
- parent2 的层级 > parent1 的层级;
- parent2 中 2 的层级 < parent1 中 1的层级(但是z-index层级是基于父级元素的);

```html
Document
```
#### z-index 不生效的情况
**1. 元素本身必须是定位元素:** relative/absolute/fixed/sticky,除了static
**2. 元素所处的父元素z-index级别不够,被别人覆盖了;**
_3. 当前设置z-index元素的父元素position:relative/absolute;(经测试是错的,可以生效)_
_4. 当前设置z-index元素为浮动元素。(经测试是错的,可以生效)_

```html
Document
```
## 移动端响应式布局方案
#### rem + js
#### rem + MediaQuery
#### rem + vw/vh
#### 百分比、vw/vh
#### 栅格布局 + MediaQuery