这是我参与「第五届青训营 」伴学笔记创作活动的第 3 天
前端与 HTML | 青训营笔记
前端入门-基础语言篇
MDN上的CSS
CSS层叠样式表
HTML 用于定义内容的结构和语义,CSS 用于设计风格和布局
使用 CSS 来更改内容的字体、颜色、大小、间距,将内容分为多列,或者添加动画及其他的装饰效果
一.CSS第一步
1.CSS用来干什么?
CSS 是用来指定文档如何展示给用户的一门语言——如网页的样式、布局、等等
一份文档是由标记语言组织起来的文本文件 —— HTML 是最常见的标记语言,但你可能也听说过其他可标记 语言,如 SVG 或 XML。
展示一份文档给用户实际上是将文档变成用户可用的文件。Browsers:如 Firefox,Chrome, 或 Edge,都可 以将文档在电脑屏幕、投影仪或打印机等设备上进行可视化。
CSS 可以用于给文档添加样式 —— 比如改变标题和链接的颜色及大小。
它也可用于创建布局 —— 比如将一个单列文本变成包含主要内容区域和存放相关信息的侧边栏区域的布局。
它甚至还可以用来做一些特效,比如动画。
2.CSS语法
h1 {
color: red;
font-size: 5em;
}
语法由一个 选择器 (selector)起头。它 选择 (selects) 了我们将要用来添加样式的 HTML 元素。在这个例子中我们为一级标题(主标题`` (en-US))添加样式。
接着输入一对大括号{ }。在大括号内部定义一个或多个形式为 属性 (property):值 (value); 的 声明 (declarations) 。每个声明都指定了我们所选择元素的一个属性,之后跟一个我们想赋给这个属性的值。
冒号之前是属性,冒号之后是值。不同的 CSS 属性 (properties) (en-US) 对应不同的合法值。在这个例子中,我们指定了 color 属性,它可以接受许多颜色值;还有 font-size 属性,它可以接收许多 size units 值。
备注: 在 MDN 上的 CSS reference 页面列举了所有的 CSS 属性页面(同时也包括其它的 CSS 特性)。另外,当你想要寻找一个 CSS 特性的更多内容时,多使用你的搜索引擎来搜索 "mdn css-feature-name" 。例如,搜索 "mdn color" 和 "mdn font-size"!
3.CSS模块
CSS 由许多模块 (modules) 构成
举个具体点的例子:如上文中的 Backgrounds and Borders 模块 — 你会发现 background-color 和 border-color 这两个属性在逻辑上相通。并且它也确实如此。
4.CSS规范
所有的标准 Web 技术 (HTML, CSS, JavaScript 等) 都被定义在一个巨大的文档中,称作 规范 specifications (或者简称为 "specs"),它是由 (像是 W3C (en-US), WHATWG, ECMA 或 Khronos (en-US)) 这些规范化组织所发布的,其中还定义了各种技术是如何工作的。
CSS 也不例外——它是由 W3C(万维网联盟) 中的一个名叫 CSS Working Group 团体发展起来的。这个团体是由浏览器厂商和其他公司中对 CSS 感兴趣的人作为代表组成的。也有其他的人员,比如受邀专家 (invited experts) ,他们作为不从属于任何组织的独立声音加入团体。
新的 CSS 特性被开发出来,或是因为某个浏览器热衷于开发新功能,或是因为 Web 设计人员与开发者要求增加一个新特性,又或是 CSS Working Group 内部的讨论决定。CSS 始终在发展,并伴随着新的特性。然而,有一件事情从始至终都未改变,那就是不让新的改变破坏旧的网站,即使是 2000 年建立的网站,如今也能正常访问!
作为一个 CSS 新手,你会发现阅读 CSS 规范 中的内容非常吃力——它旨在为工程师在用户代理 (user agents) 中实现对 CSS 各种特性的支持,而不是作为一本为 Web 开发者理解 CSS 内容的教程。即使是有经验的开发者,也更倾向于使用 MDN 文档或者其它教程。但是,知晓它的存在,理解 CSS、规范 和 浏览器支持(见下文)之间的关系是很有价值的。
5.浏览器支持
当一个浏览器支持 CSS 后,我们就可以用它来进行 Web 开发了。这意味着我们写在 CSS 文件中的代码可以被指令执行,展示到荧幕中。在 CSS 如何工作一节中我们会学习到更多的相关知识。但是让所有的浏览器都同时支持一个 CSS 新特性是不现实的,通常都会一个空档期——一些浏览器已经支持而另一些仍未支持。因此,查看特性的实现状态是非常有用的。在 MDN 上的每个属性的页面中都标有它们对应的状态,你可以通过这种方法来查看你是否可以去使用它
7.如何构建CSS
A、外部样式表
外部样式表是指将 CSS 编写在扩展名为.css 的单独文件中,并从 HTML <link> 元素引用它的情况
B、内部样式表
内部样式表是指不使用外部 CSS 文件,而是将 CSS 放在 HTML 文件](https://developer.mozilla.org/zh-CN/docs/Web/HTML/Element/head)标签里的[标签之中。
C、内联样式表
内联样式表存在于 HTML 元素的 style 属性之中。其特点是每个 CSS 表只影响一个元素
8.选择器
如果属性未知或某个值对给定属性无效,则声明被视为无效,并被浏览器的 CSS 引擎完全忽略。
在 CSS(和其他网络标准) 中,当语言表达存在不确定性时,美国的拼写被视作公认的标准。例如,颜色应该始终拼写为 color。colour 是不起作用的。
9.函数
10.CSS如何运作
- 浏览器载入 HTML 文件(比如从网络上获取)。
- 将 HTML 文件转化成一个 DOM(Document Object Model),DOM 是文件在计算机内存中的表现形式,下一节将更加详细的解释 DOM。
- 接下来,浏览器会拉取该 HTML 相关的大部分资源,比如嵌入到页面的图片、视频和 CSS 样式。JavaScript 则会稍后进行处理,简单起见,同时此节主讲 CSS,所以这里对如何加载 JavaScript 不会展开叙述。
- 浏览器拉取到 CSS 之后会进行解析,根据选择器的不同类型(比如 element、class、id 等等)把他们分到不同的“桶”中。浏览器基于它找到的不同的选择器,将不同的规则(基于选择器的规则,如元素选择器、类选择器、id 选择器等)应用在对应的 DOM 的节点中,并添加节点依赖的样式(这个中间步骤称为渲染树)。
- 上述的规则应用于渲染树之后,渲染树会依照应该出现的结构进行布局。
- 网页展示在屏幕上(这一步被称为着色)。
二.CSS构建基础
1.层叠与继承
(1).冲突原则
(2).优先级:
- 一个元素选择器不是很具体,则会选择页面上该类型的所有元素,所以它的优先级就会低一些。
- 一个类选择器稍微具体点,则会选择该页面中有特定
class属性值的元素,所以它的优先级就要高一点。
(3).继承:一些设置在父元素上的 CSS 属性是可以被子元素继承的,有些则不能。
(4).控制继承:CSS 为控制继承提供了五个特殊的通用属性值。每个 CSS 属性都接收这些值。
A、inherit设置该属性会使子元素属性和父元素相同。实际上,就是“开启继承”。
B、initial将应用于选定元素的属性值设置为该属性的初始值。
C、revert (en-US)将应用于选定元素的属性值重置为浏览器的默认样式,而不是应用于该属性的默认值。在许多情况下,此值的作用类似于 unset。
D、revert-layer (en-US)将应用于选定元素的属性值重置为在上一个层叠层中建立的值。
E、unset将属性重置为自然值,也就是如果属性是自然继承那么就是 inherit,否则和 initial 一样
(5).CSS规则,重要性因素排序:
1)资源顺寻
可以理解为后面的规则覆盖前面的规则,直到最后一个开始设置样式。
资源顺序仅在规则的优先级相同时才体现出来。
2)优先级
你会发现在一些情况下,有些规则在最后出现,但是却应用了前面的具有冲突的规则。这是因为前面的有更高的优先级——它范围更小,因此浏览器就把它选择为元素的样式。
就像前面看到的,类选择器的权重大于元素选择器,因此类上定义的属性将覆盖应用于元素上的属性。
这里需要注意虽然我们考虑的是选择器,以及应用在选中对象上的规则,但不会覆盖所有规则,只覆盖相同的属性。
这样可以避免重复的 CSS。一种常见的做法是给基本元素定义通用样式,然后给不同的元素创建对应的类。举个例子,在下面的样式中我给 2 级标题定义了通用样式,然后创建了一些类只修改部分属性的值。最初定义的值应用于所有标题,然后更具体的值通过对应类来实现。
一个选择器的优先级可以说是由三个不同的值(或分量)相加,可以认为是百(ID)十(类)个(元素)——三位数的三个位数:
- ID:选择器中包含 ID 选择器则百位得一分。
- 类:选择器中包含类选择器、属性选择器或者伪类则十位得一分。
- 元素:选择器中包含元素、伪元素选择器则个位得一分。
| 选择器 | ID | 类 | 元素 | 优先级 |
|---|---|---|---|---|
h1 | 0 | 0 | 1 | 0-0-1 |
h1 + p::first-letter | 0 | 0 | 3 | 0-0-3 |
li > a[href*="en-US"] > .inline-warning | 0 | 2 | 2 | 0-2-2 |
#identifier | 1 | 0 | 0 | 1-0-0 |
button:not(#mainBtn, .cta) | 1 | 0 | 1 | 1-0-1 |
3)重要程度
- 前面两个选择器都是链接背景颜色的样式——第二个赢了使得背景变成蓝色,因为它多了一个 ID 选择器:优先级 2-0-1 vs. 1-0-1。
- 第三四个选择器都是链接文本颜色样式——后者赢了使得文本变成白色,因为它虽然少一个元素选择器,但是多了一个类选择器。所以优先级是 1-1-3 vs. 1-0-4。
- 第 5 到 7 个选择器都是鼠标悬停时链接边框样式。第六个显然输给了第五个,优先级是 0-2-3 vs. 0-2-4——少了个元素选择器。第七个,比第五第六都高——子选择器数量相同,但是有一个元素选择器变成类选择器。所以最后优先级是 0-3-3 vs. 0-2-3 和 0-2-4
备注: 每一个选择器类编都有它自己的优先级等级,它们不会被具有较低优先级的选择器覆盖。例如,权重为一百万的类选择器不会覆盖权重为一的 ID 选择器。
评估优先级的最佳方法是对不同的优先级等级单独进行评分,并从最高的等级开始,必要时再计算低优先级等级的权重。即,仅当某一列的优先级权重相同时,你才需要评估下一列;否则,你可以直接忽略低等级的选择器,因为它们无法覆盖高优先级等级的选择器。
(6).内联样式
内联样式,即 style 属性内的样式声明,优先于所有普通的样式,无论其优先级如何。这样的声明没有选择器,但它们的优先级可以理解为 1-0-0-0;即无论选择器中有多少个 ID,它总是比其它任何优先级的权重都要高。
备注:有一个特殊的 CSS 可以用来覆盖所有上面所有优先级计算,不过需要很小心的使用——!important。用于修改特定属性的值,能够覆盖普通规则的层叠。
备注: 了解 !important 是为了在阅读别人代码的时候知道有什么作用。但是,强烈建议除了非常情况不要使用它。 !important 改变了层叠的常规工作方式,它会使调试 CSS 问题非常困难,特别是在大型样式表中。
- 你会发现第三个规则
color和padding的值被应用了,但是background-color没有。为什么?应该三个都应用,因为顺序规则是后面覆盖前面。 - 无论如何,上面的规则赢了,因为类选择器比元素选择器有更高的优先级。
- 两个元素都有
betterclass,但是第二个有id。因为 ID 选择器比类选择器优先级更高(一个页面只能有一个独特的 ID,但是很多元素都有相同的类——ID 对于目标非常独特),红色背景和 1px 黑色边框应该都被应用到第二个元素,第一个元素应该是灰色背景和 no border,根据类选择器。 - 第二个元素有红色背景但是没有边框。为什么?因为
!important声明在第二条规则里——在border: none后面,说明即使计算优先级低,这个属性也使用这个值。
(7).CSS位置的影响
CSS 声明的优先级取决于定义它的样式表和级联层。
相互冲突的声明将按以下顺序应用,后一种声明将覆盖前一种声明:
用户代理样式表中的声明(例如,浏览器的默认样式,在没有设置其他样式时使用)。
用户样式表中的常规声明(由用户设置的自定义样式)。
作者样式表中的常规声明(这些是我们 web 开发人员设置的样式)。
作者样式表中的 !important 声明
用户样式表中的 !important 声明
用户代理样式表中的 !important 声明