概述
层叠样式表(Cascading Style Sheets,简称CSS)是描述HTML文档呈现方式的标准语言。CSS3并非单一的规范文档,而是CSS规范的一个模块化集合,由W3C的CSS工作组分模块逐步制定和发布。这种模块化的策略使得浏览器可以独立实现各个特性,而无需等待整个规范的完成。
CSS的核心设计理念包含三个关键词:层叠(Cascading)、继承(Inheritance)与特异性(Specificity)。层叠机制决定了当多个样式规则应用于同一元素时,哪一个规则最终生效。继承机制使得某些属性值可以从父元素传递给子元素,减少了重复声明。特异性则是一套计算选择器权重的算法,用于在层叠冲突时判定优先级。
CSS3的演进带来了选择器的极大丰富、布局系统的根本变革(从基于浮动和定位的hack式布局转向Flexbox和Grid的声明式布局)、视觉效果的质的飞跃(圆角、阴影、渐变不再需要图片),以及动画能力的原生支持(transition与animation)。这些进步使CSS从一种简单的样式描述语言,进化为功能强大的视觉设计与交互实现工具。
选择器系统
选择器是CSS的根基,它定义了样式规则应用于哪些元素。CSS3极大地扩展了选择器的表达能力,使开发者能够更精确地定位目标元素,减少不必要的class或id污染。
属性选择器
CSS3增强了属性选择器的能力。E[attr]选择具有attr属性的E元素;E[attr="val"]选择attr属性值恰好等于val的元素;E[attr~="val"]选择attr属性值是以空格分隔的列表且其中包含val的元素,常用于匹配class列表中的某个类名;E[attr|="val"]选择attr属性值等于val或以val-开头的元素,常用于语言代码匹配。
CSS3新增的三个属性选择器更为强大:E[attr^="val"]匹配属性值以val开头的元素;E[attr$="val"]匹配属性值以val结尾的元素;E[attr*="val"]匹配属性值包含val子串的元素。这三个选择器在文件类型图标、链接样式区分等场景中极为实用。
结构伪类选择器
:nth-child(n)选择父元素的第n个子元素,n可以是具体数字、关键字(odd/even)或公式(如2n+1)。:nth-last-child(n)从末尾开始计数。:first-child与:last-child分别是:nth-child(1)与:nth-last-child(1)的简写。:only-child选择唯一的子元素。
:nth-of-type(n)与:nth-child(n)的区别至关重要:前者在同类型元素中计数,后者在所有子元素中计数。当父元素包含混合类型的子元素时,这一区别尤为明显。:first-of-type、:last-of-type、:only-of-type遵循类似的逻辑。
其他重要伪类
:not(selector)选择不匹配给定选择器的元素,它接受一个简单选择器作为参数。:empty选择没有子元素(包括文本节点)的元素。:target选择当前URL片段标识符指向的元素。:checked选择被选中的表单控件。:disabled与:enabled分别选择禁用和可用的表单控件。:valid与:invalid配合HTML5表单验证使用。
伪元素
::before与::after在元素内容的前后插入生成的内容,是装饰性元素最常用的技术。::first-letter与::first-line分别选择块级元素的首字母和首行,常用于排版增强。::selection用于设置用户选中文本的样式。CSS3使用双冒号语法区分伪元素与伪类,但单冒号写法仍被兼容。
选择器性能提示:浏览器解析选择器是从右向左进行的。最右侧的选择器(关键选择器)决定了初始匹配范围。避免使用过于宽泛的关键选择器(如*或标签名),尽量使用class作为关键选择器以提高匹配效率。
盒模型
CSS盒模型是理解页面布局的基础。每个元素在页面中都被视为一个矩形盒子,由内容区(content)、内边距(padding)、边框(border)和外边距(margin)四层构成。在标准盒模型(content-box)中,width与height属性仅指定内容区的大小,元素的实际占用空间需要加上padding和border。
CSS3引入的box-sizing属性允许开发者切换盒模型计算方式。当设置为border-box时,width与height属性包含了content、padding和border的总和,这使得尺寸计算更加直观。许多CSS框架(如Bootstrap)会在全局设置border-box,以简化布局计算。
margin的折叠(Margin Collapsing)是盒模型中一个容易混淆的概念。当两个垂直相邻的块级元素的外边距相遇时,它们不会简单相加,而是折叠为较大的那个值。这一行为仅发生在常规文档流中的块级元素之间,浮动元素、绝对定位元素、inline-block元素以及根元素的外边距不会折叠。
CSS3还引入了outline属性,它与border类似但不会影响元素的尺寸计算,也不占据布局空间。outline-offset属性可以控制outline与边框之间的距离,支持负值使outline向内收缩。这些特性常用于实现聚焦状态的视觉提示。
布局系统
CSS布局经历了从表格布局到浮动布局,再到Flexbox和Grid布局的演进。现代CSS开发应当优先使用Flexbox和Grid,仅在必要时回退到传统技术。
Flexbox 弹性布局
Flexbox(Flexible Box Layout)是一维布局系统,专为处理行或列中的项目排列而设计。通过设置容器的display属性为flex或inline-flex,其子元素成为弹性项目(flex item)。
主轴方向由flex-direction控制(row、row-reverse、column、column-reverse)。flex-wrap控制项目是否换行(nowrap、wrap、wrap-reverse)。justify-content定义项目在主轴上的对齐方式(flex-start、flex-end、center、space-between、space-around、space-evenly)。align-items定义项目在交叉轴上的对齐方式(stretch、flex-start、flex-end、center、baseline)。align-content定义多行项目在交叉轴上的对齐方式。
弹性项目自身也有若干重要属性:flex-grow定义项目的放大比例,flex-shrink定义缩小比例,flex-basis定义项目在分配剩余空间前的初始大小。flex是这三个属性的简写,推荐始终使用简写形式。order属性可以改变项目的视觉顺序(不影响DOM顺序和可访问性)。align-self允许单个项目覆盖容器的align-items设置。
Grid 网格布局
CSS Grid Layout是二维布局系统,可以同时处理行和列的排列,非常适合构建复杂的页面整体结构。通过display: grid或display: inline-grid启用网格布局。
网格轨道(track)通过grid-template-columns和grid-template-rows定义。可以使用绝对长度(px、rem)、百分比、fr单位(剩余空间的分数)以及repeat()函数来定义轨道。minmax()函数可以指定轨道的最小和最大尺寸。auto-fill与auto-fit关键字配合repeat()可以实现响应式的自动列数调整。
网格线(grid line)是划分网格轨道的线条,可以通过编号或名称引用。网格区域(grid area)是由四条网格线围成的矩形区域。grid-template-areas属性提供了一种直观的ASCII艺术式布局定义方式,通过命名区域来安排元素位置。
grid-gap(简写为gap)属性控制网格单元之间的间距。这一属性后来被推广到Flexbox中,成为通用的间距控制方案。grid-auto-flow控制自动放置算法的行为,row、column和dense三个值分别对应按行填充、按列填充和尽可能紧密填充(dense模式会尝试填补前面的空白区域)。
定位与层叠
position属性有五个取值:static(默认值,正常文档流)、relative(相对定位,相对于自身正常位置偏移)、absolute(绝对定位,相对于最近的非static定位祖先元素)、fixed(固定定位,相对于视口)和sticky(粘性定位,在阈值前表现为relative,达到阈值后表现为fixed)。
z-index控制定位元素的层叠顺序,仅对position值不为static的元素有效。层叠上下文(Stacking Context)是一个重要的概念:当元素创建了新的层叠上下文时,其内部的z-index只在该上下文内部比较。创建层叠上下文的方式包括:设置opacity小于1、设置transform不为none、设置filter不为none、设置isolation为isolate等。
视觉效果
CSS3在视觉效果方面的增强使网页设计摆脱了早期扁平单调的局限,能够创造出丰富的质感与深度。
border-radius属性用于创建圆角效果,可以接受一至四个值,分别对应左上、右上、右下、左下四个角。当使用百分比值且元素为正方形时,可得到完美的圆形。椭圆角可以通过斜杠语法实现,如border-radius: 50% / 20%。
box-shadow属性为元素添加阴影效果,语法为:水平偏移 垂直偏移 模糊半径 扩展半径 颜色。可以添加inset关键字创建内阴影。多重阴影通过逗号分隔实现,后面的阴影位于上层。阴影是提升界面层次感的重要手段,但应避免过度使用导致视觉混乱。
text-shadow为文字添加阴影,语法与box-shadow类似但不支持扩展半径和inset。合理的文字阴影可以增强文字在复杂背景上的可读性,或创造浮雕、发光等特殊效果。
渐变(Gradient)是CSS3中强大的背景填充方式。linear-gradient()创建线性渐变,通过角度或方向关键字(to top、to right等)控制渐变方向,通过色标(color stop)定义颜色过渡点。radial-gradient()创建径向渐变,可以指定形状(circle或ellipse)和大小。conic-gradient()创建圆锥渐变,适用于饼图等场景。repeating-linear-gradient()和repeating-radial-gradient()可以创建重复的渐变图案。
背景相关的增强包括background-size(控制背景图尺寸,支持cover和contain关键字)、background-origin(定义背景定位的参考区域)、background-clip(定义背景绘制区域,支持text值实现文字裁剪效果)以及多背景支持(通过逗号分隔多个背景层)。
透明度控制方面,opacity属性设置整个元素的不透明度,而rgba()和hsla()颜色函数可以仅设置背景色的透明度,不影响子元素。CSS Color Module Level 4引入了新的颜色空间(lab、lch、color()等),为更精确的色彩管理提供了可能。
变换与动画
CSS3的变换(Transform)和动画(Animation)功能使网页从静态展示走向动态交互,且这些效果由浏览器的合成器线程处理,通常不会触发重排和重绘,性能表现优异。
变换 Transform
transform属性接受一个或多个变换函数。translate()、translateX()、translateY()实现位移;scale()、scaleX()、scaleY()实现缩放;rotate()实现旋转(正值为顺时针);skew()实现倾斜。变换的原点由transform-origin控制,默认为元素中心。
3D变换通过perspective属性开启透视效果,transform-style: preserve-3d使子元素保留3D空间关系。rotateX()、rotateY()、rotateZ()实现三维旋转,translateZ()实现Z轴位移。backface-visibility控制元素背面是否可见,在实现卡片翻转效果时尤为重要。
过渡 Transition
transition属性实现属性值变化的平滑过渡。需要指定过渡属性(transition-property,可使用all)、持续时间(transition-duration)、时间函数(transition-timing-function)和延迟时间(transition-delay)。
时间函数控制过渡的速度曲线。ease(默认)先快后慢再快;linear匀速;ease-in加速;ease-out减速;ease-in-out先加速后减速。cubic-bezier()允许自定义贝塞尔曲线,实现更精细的速度控制。steps()函数实现阶梯式过渡,常用于实现逐帧动画效果。
动画 Animation
@keyframes规则定义动画的关键帧序列,from与to分别等价于0%与100%。在每个关键帧中,可以定义任意CSS属性的目标值。动画通过animation属性应用到元素上,该属性是多个子属性的简写:animation-name(引用的@keyframes名称)、animation-duration(持续时间)、animation-timing-function(时间函数)、animation-delay(延迟)、animation-iteration-count(播放次数,infinite表示无限循环)、animation-direction(播放方向,normal、reverse、alternate、alternate-reverse)、animation-fill-mode(动画结束后的状态,forwards保持最后一帧、backwards应用第一帧样式于延迟期间、both两者兼具)以及animation-play-state(运行或暂停)。
CSS动画相比JavaScript动画的优势在于:由浏览器优化执行,通常运行在合成器线程,不阻塞主线程;可以方便地利用硬件加速;声明式语法更易于维护。但对于需要复杂逻辑控制、物理模拟或用户交互实时响应的动画,JavaScript动画(如requestAnimationFrame)仍然更为合适。
will-change属性可以提前告知浏览器元素即将发生的变化,使浏览器能够预先进行优化(如创建独立的合成层)。但应谨慎使用,过度创建合成层会消耗额外的内存。常见的用法是will-change: transform或will-change: opacity。
响应式设计
响应式网页设计的核心理念是:同一套HTML和CSS代码,能够根据设备的屏幕尺寸、分辨率、方向等特性,自适应地呈现最佳的布局与体验。这一理念由伊桑·马科特(Ethan Marcotte)于2010年提出,现已成为现代网页开发的标准实践。
媒体查询(Media Queries)是响应式设计的核心技术。通过@media规则,可以针对不同的媒体特性应用不同的样式。常见的查询条件包括:min-width/max-width(视口宽度)、min-height/max-height(视口高度)、orientation(方向,portrait或landscape)、resolution(分辨率)等。逻辑运算符and、not、only以及逗号分隔的或关系,支持构建复杂的查询条件。
移动优先(Mobile First)与桌面优先(Desktop First)是两种响应式策略。移动优先从基础样式开始面向小屏幕,然后通过min-width媒体查询逐步增强大屏幕体验。这种策略的优点是移动端加载的CSS更精简,且符合渐进增强的理念。桌面优先则相反,从大屏幕布局开始,通过max-width媒体查询适配小屏幕。
相对单位在响应式设计中至关重要。rem单位相对于根元素(html)的字体大小,适合用于尺寸和间距的统一缩放。em单位相对于父元素的字体大小,适合用于组件内部的相对尺寸。vw和vh单位分别相对于视口宽度和高度的百分比,1vw等于视口宽度的1%。vmin和vmax分别取vw和vh中的较小值和较大值。ch单位等于当前字体中数字0的宽度,适合用于限制文本行的最大宽度(通常建议每行45至75个字符)。
响应式图片技术包括:srcset属性提供不同分辨率的图片源,由浏览器根据设备像素密度选择最合适的图片;sizes属性告知浏览器图片在不同断点下的显示尺寸,辅助浏览器做出最优选择;picture元素配合source元素,可以根据媒体查询条件(如视口宽度)选择不同的图片源,甚至提供完全不同的图片格式(如WebP回退到JPEG)。
容器查询(Container Queries)是CSS的新兴特性,它允许元素根据其所在容器(而非视口)的尺寸来调整样式。这解决了组件级响应式的难题:同一个组件在不同页面区域可能拥有不同的可用空间,传统的媒体查询无法处理这种场景。通过设置容器的container-type属性(如inline-size),其子元素可以使用@container规则进行容器尺寸查询。