目录
scss是什么
scss和css比较
scss的使用
声明变量
区分默认变量
区分全局变量和局部变量
嵌套语法
选择器嵌套
基本嵌套
嵌套中的父选择器引用(&)
嵌套的注意事项
嵌套的嵌套
属性嵌套
基本属性嵌套
嵌套的注意事项
继承
基本用法
继承的注意事项
应用场景
占位符 %
定义占位符
继承占位符
优势和适用场景
注意事项
混合@mixin
定义混合
调用混合
例子
优势和适用场景
注意事项
SCSS使用条件语句
@if 语句
@else 和 @else if 语句
条件语句的嵌套
结论
SCSS中的三种循环
@for 循环
@each 循环
@while 循环
总结
自定义函数及使用
定义自定义函数
使用自定义函数
注意事项
课后练习
scss是什么
SCSS(Sassy CSS)是CSS的一种预处理器语言,它在CSS的基础上提供了更多的功能和灵活性,使得样式表的编写和管理更加高效和便捷。
以下是SCSS的一些优势:
- 变量(Variables):SCSS允许使用变量来存储颜色、字体大小等数值,使得在整个样式表中统一调整这些值变得更加方便和可维护。
- 嵌套(Nested Rules):可以在SCSS中使用嵌套规则来组织样式,使得代码结构更加清晰。例如,可以将某个元素的伪类样式写在其父元素的样式块中,而不是分开多处书写。
- 混合(Mixins):混合是一种将一组样式属性集合成一个可重用块的方式。这样可以避免重复书写相同的样式代码,提高了代码的复用性和可读性。
- 导入(Inline Imports):可以通过@import规则将多个SCSS文件合并为一个文件。这种方式有助于将样式表分割成逻辑单元,并且可以根据需要灵活地组织和管理。
- 继承(Extend):SCSS支持通过@extend关键字实现样式的继承,这可以使得样式表更加模块化和可维护。
- 运算(Operations):SCSS允许在样式表中进行数学运算,例如加减乘除,这对于处理一些动态样式的计算很有帮助。
- 模块化(Modularity):SCSS的特性使得样式表更加模块化和结构化,尤其在大型项目中,能够更好地管理和维护样式。
总结来说,SCSS不仅保留了CSS的所有功能,还引入了诸如变量、嵌套、混合、导入等高级特性,这些功能使得开发者能够更加高效地编写和管理样式表,是现代前端开发中常用的工具之一。
scss和css比较
语法:
- CSS:基本的层叠样式表语法,规则是通过选择器、属性和值来定义。
- SCSS:SCSS是CSS的一种预处理器语言,它提供了更多的功能和语法,如变量、嵌套规则、混合、导入等,这些使得样式表的编写更加灵活和高效。
可读性和维护性:
- CSS:在较大的项目中,CSS文件可能会变得非常冗长和难以维护,因为它缺乏结构化和模块化的特性。
- SCSS:SCSS支持变量和嵌套规则,这些特性使得代码更具可读性和维护性。通过使用变量和混合,可以减少重复代码的书写,同时嵌套规则可以更清晰地表达HTML结构的层次关系。
功能扩展:
- CSS:标准的CSS只能做基本的样式定义和选择器匹配。
- SCSS:SCSS引入了混合、继承、运算等高级功能,这些功能使得样式表更加灵活和强大,能够更好地应对复杂的样式需求。
兼容性:
- CSS:浏览器直接支持CSS,不需要额外的编译步骤。
- SCSS:SCSS需要通过编译器将其转换为普通的CSS文件,然后才能被浏览器理解和应用。
学习曲线:
- CSS:学习CSS相对简单,只需了解基本的选择器、属性和值的组合即可。
- SCSS:学习SCSS需要掌握其特有的语法和功能,例如变量、混合、嵌套等,这需要一定的学习和适应过程。
综上所述,SCSS相对于普通的CSS来说,提供了更多的工具和特性来简化样式表的编写和维护,尤其适合大型和复杂项目的开发。然而,对于小型项目或者简单的样式需求,普通的CSS可能更加直接和方便。
scss的使用
在学习scss前,先在vscode安装两个插件来将scss转换为普通的CSS文件,以便后续学习!
在插件商店搜索sass,下载以下两个插件并重启vscode!
声明变量
在SCSS中声明变量非常简单,可以使用$符号来定义变量。
下面是一个简单的例子,演示如何在SCSS中声明和使用变量:
// 定义变量
$primary-color: #3498db;
$secondary-color: #2ecc71;
// 使用变量
body {
background-color: $primary-color;
}
a {
color: $secondary-color;
}
在上面的例子中,我们定义了两个变量$primary-color和$secondary-color,分别用来存储主要颜色和次要颜色。然后,我们可以在样式规则中使用这些变量,以便在整个样式表中保持颜色的一致性和易于修改性。
当SCSS文件被编译成普通的CSS文件时,所有的变量会被替换为其对应的值,因此最终生成的CSS文件中不会包含任何变量声明。
区分默认变量
在SCSS中,可以使用默认变量来确保变量在未定义时有一个备用值。这在处理主题化或配置样式时特别有用。
下面是如何声明和使用默认变量的示例:
// 声明变量,并设置默认值
$primary-color: #3498db !default;
$secondary-color: #2ecc71 !default;
// 使用变量
body {
background-color: $primary-color;
}
a {
color: $secondary-color;
}
在上面的例子中,我们使用了!default标记来定义默认值。这意味着如果在引入该SCSS文件之前没有其他地方定义$primary-color或$secondary-color,则它们将使用指定的默认值(#3498db和#2ecc71)。如果在引入该文件之前已经定义了这些变量,那么默认值将被忽略。
使用默认变量的好处在于,它允许你在不覆盖已定义变量的情况下为变量提供备用值。这对于创建主题或在多个样式文件中共享变量特别有用。
区分全局变量和局部变量
- 全局变量:全局变量是在选择器外或混合器/函数外部声明的变量。它们可以在整个样式表中访问,并且如果在多个文件中定义了相同的全局变量,则它们的值将保持一致。
- 局部变量:局部变量是在选择器内部或混合器/函数内部定义的变量。它们只能在其定义的作用域内使用,离开该作用域后就不再有效。
注意:局部变量覆盖全局变量
当在局部作用域中重新声明一个与全局变量同名的变量时,局部变量会覆盖全局变量的值。这允许在不影响全局的情况下,为特定选择器或混合器定义不同的变量值。
使用 !global 关键字将局部变量变为全局变量
SCSS提供了!global关键字,可以将局部变量显式地声明为全局变量。这使得局部变量的值在其声明的地方被提升到全局范围内,覆盖任何已存在的同名全局变量。
示例:
// 全局变量
$primary-color: #3498db;
.button {
// 局部变量,覆盖全局变量
$primary-color: #cc582e;
background-color: $primary-color; // 使用局部变量值
}
// 使用 !global 将局部变量变为全局变量
$primary-color: #cddb34;
.button {
// 使用 !global 将局部变量变为全局变量
$primary-color: #2ecc71 !global;
}
body {
background-color: $primary-color; // 这里使用的是已变为全局的 $primary-color
}
在第一个示例中,.button选择器内部的局部变量$primary-color覆盖了全局变量的值。而在第二个示例中,通过使用!global关键字,将.button选择器内部的局部变量转变为全局变量,从而影响了全局范围内的变量值。
嵌套语法
选择器嵌套
基本嵌套
选择器嵌套允许将子选择器的样式规则嵌套在父选择器内部,例如:
// SCSS代码
.navbar {
background-color: #333;
padding: 10px;
ul {
list-style: none;
margin: 0;
padding: 0;
li {
display: inline-block;
margin-right: 10px;
a {
text-decoration: none;
color: #fff;
&:hover {
text-decoration: underline;
}
}
}
}
}
上述代码中,.navbar选择器包含了一个嵌套的 ul、li 和 a 子选择器。这种嵌套结构使得样式规则更加清晰和易于管理。
嵌套中的父选择器引用(&)
在SCSS中,& 符号用于引用父选择器,特别是在伪类或伪元素的情况下很有用。例如,使用 &:hover 来引用当前选择器的父选择器并添加 :hover 状态样式。
.button {
background-color: #3498db;
color: #fff;
padding: 8px 16px;
border: none;
text-align: center;
text-decoration: none;
display: inline-block;
&:hover {
background-color: #2980b9;
}
}
嵌套的注意事项
- 选择器深度: 避免过深的选择器嵌套,因为它可能增加样式优先级,导致样式覆盖和维护困难。
- 可读性: 使用选择器嵌套时要注意保持代码的可读性和清晰性,避免过度复杂的嵌套结构。
- 性能: 嵌套结构可能会增加生成的CSS文件的大小,但通常可以通过合理的样式组织和编写来优化。
嵌套的嵌套
SCSS允许多层级的选择器嵌套,例如:
.container {
.row {
.col {
width: 100%;
}
}
}
属性嵌套
在SCSS中,除了选择器嵌套外,还有属性嵌套的功能,这是另一个使样式表更整洁和易于管理的特性。属性嵌套允许将相关的属性组织在一起,类似于对象的形式。
基本属性嵌套
属性嵌套可以用来将相关的属性放在一个代码块内,例如:
.navbar {
font: {
family: Arial, sans-serif;
size: 16px;
weight: bold;
}
margin: {
top: 10px;
bottom: 15px;
}
padding: {
left: 20px;
right: 20px;
}
}
上面的示例中,font、margin 和 padding 块内部分别包含了相关的属性。这种组织方式使得每个块内的属性更加清晰,也更容易修改和维护。
嵌套的注意事项
- 支持的属性: 不是所有的CSS属性都支持嵌套,通常是那些可以接受键值对的属性,比如 font、margin、padding、border 等。
- 可读性: 使用属性嵌套时,要确保代码的可读性和清晰性,避免过度嵌套和复杂的结构。
- 嵌套的嵌套: 你也可以在属性嵌套中再次嵌套其他属性,这种方式可以进一步组织和结构化你的样式。
继承
在 SCSS 中,继承(Extend)是一种非常有用的特性,它允许一个选择器继承另一个选择器的样式规则。这种功能可以减少重复的 CSS 代码,并使样式表更加模块化和易于维护。
基本用法
使用 @extend 关键字可以实现选择器的继承。例如:
%message-shared {
border: 1px solid #ccc;
padding: 10px;
color: #333;
}
.success-message {
@extend %message-shared;
background-color: lightgreen;
}
.error-message {
@extend %message-shared;
background-color: lightcoral;
}
上面的例子中,%message-shared 是一个占位符选择器(Placeholder Selector),它定义了一组通用的样式。.success-message 和 .error-message 分别继承了 %message-shared 的样式,并且添加了各自的背景颜色。
继承的注意事项
- 选择器顺序: 继承会生成一长串的选择器,这可能会影响样式的优先级。确保在使用 @extend 时,选择器的顺序和位置是正确的,以避免不必要的优先级问题。
- 限制: 继承的选择器必须出现在被继承选择器之后。这意味着,如果你的 SCSS 文件中定义了一个选择器,在后续的代码中使用 @extend 继承它的样式,则这个继承只有在定义后才会生效。
- 占位符选择器 vs 类选择器: 使用 % 开头的占位符选择器通常比直接的类选择器更适合作为继承的目标,因为它们不会在编译后生成多余的选择器。而类选择器则会在每个使用它的地方生成重复的样式,增加文件大小和复杂度。
应用场景
继承特别适合那些具有共同特征的选择器,比如按钮组件、消息提示框等。通过继承,可以在不同的场景中重用相同的样式规则,同时保持代码的整洁和可维护性。
综上所述,SCSS 中的继承是一个强大的工具,能够帮助你避免样式重复,保持代码的模块化和清晰度,但在使用时需要注意选择器的顺序和位置,以及合理使用占位符选择器来最大化其效果。
占位符 %
占位符 % 在 SCSS 中是一种特殊的选择器,它通常用于定义可以被继承但不会生成实际 CSS 输出的样式规则。具体来说:
定义占位符
%placeholder-selector {
// 样式规则
}
在上面的例子中,%placeholder-selector 是一个以 % 开头的占位符选择器。它定义了一组样式规则,但在编译生成的 CSS 中不会出现对应的选择器名字。
继承占位符
.some-class {
@extend %placeholder-selector;
// 可选的额外样式
}
使用 @extend 关键字可以让 .some-class 继承 %placeholder-selector 的样式。这意味着 .some-class 将会应用 %placeholder-selector 中定义的所有样式规则,同时生成相应的 CSS 输出。
优势和适用场景
- 减少重复: 占位符选择器使得可以定义一组通用的样式规则,并在需要时通过继承来重用这些规则,避免代码重复。
- 模块化: 占位符选择器有助于代码的模块化和可维护性,特别是在大型项目中,可以提高样式表的结构清晰度。
- 避免冗余: 相比使用类选择器,占位符选择器不会生成多余的选择器,从而减少 CSS 文件的大小。
注意事项
- 顺序和位置: 使用 @extend 继承占位符选择器时,被继承的占位符选择器必须在使用它的选择器之前定义,否则可能导致意外的样式层级问题。
- 混用: 可以将占位符选择器和普通类选择器结合使用,但需谨慎处理,避免产生意外的 CSS 输出。
总结来说,占位符选择器 % 是 SCSS 中一个强大的工具,可以帮助开发者提高样式表的重用性和可维护性,同时减少不必要的 CSS 冗余。
混合@mixin
在 SCSS 中,混合(Mixin)是另一种非常强大的特性,它允许将一组样式规则封装在一个可重用的代码块中,然后在需要的地方引用。与占位符选择器 % 不同,混合是可以直接生成 CSS 输出的,因此它适合那些需要在多个地方使用相同样式的情况。
定义混合
@mixin mixin-name($parameter1, $parameter2, ...) {
// 样式规则使用参数
}
在上面的例子中,@mixin 关键字定义了一个名为 mixin-name 的混合,可以接受多个参数(如果需要的话),并在其中定义一组样式规则。
调用混合
.some-class {
@include mixin-name(value1, value2, ...);
// 可选的额外样式
}
使用 @include 关键字可以在选择器中调用混合,并传递参数给它。这样,.some-class 将会应用混合中定义的样式规则,并将传递的参数值应用到对应的参数变量上。
例子
@mixin button-style($background-color, $text-color) {
display: inline-block;
padding: 10px 20px;
border: none;
border-radius: 4px;
background-color: $background-color;
color: $text-color;
text-align: center;
text-decoration: none;
font-size: 16px;
cursor: pointer;
transition: background-color 0.3s ease;
&:hover {
background-color: darken($background-color, 10%);
}
}
.button-primary {
@include button-style(#3498db, #fff);
}
.button-secondary {
@include button-style(#2ecc71, #fff);
}
优势和适用场景
- 灵活性: 混合允许传递参数,可以根据需要动态生成不同的样式输出,使得样式更加灵活和可定制。
- 可读性: 将常用的样式规则封装在混合中,可以提高代码的可读性和维护性,特别是在多个地方需要相同样式的情况下。
- 复用性: 可以在不同的选择器和文件中多次调用同一个混合,避免样式的重复定义,减少代码量。
注意事项
- 命名冲突: 确保混合名称不会与现有的 CSS 类名或其他混合名称冲突,避免意外的样式覆盖或错误。
- 参数传递: 在调用混合时,确保传递的参数类型和顺序与混合定义的要求一致,以避免编译错误或意外行为。
- 性能影响: 大量使用混合可能会增加生成的 CSS 文件大小,因此在使用时要谨慎考虑其对性能的影响。
总结来说,混合 @mixin 是 SCSS 中用于封装和重用样式规则的一种强大工具,可以显著提高 CSS 的可维护性和灵活性,适合各种复杂和重复的样式需求。
SCSS使用条件语句
在 SCSS 中,条件语句允许根据特定条件动态地生成 CSS 样式。SCSS 的条件语句类似于其他编程语言中的条件语句,包括 @if、@else if 和 @else。
@if 语句
@if 语句允许根据一个条件来生成样式。语法如下:
$use-rounded-corners: true;
.button {
@if $use-rounded-corners {
border-radius: 4px;
}
}
在上面的例子中,如果 $use-rounded-corners 变量的值为 true,则生成 .button 类的样式,包含 border-radius: 4px;。如果条件为 false,则不会生成这部分样式。
@else 和 @else if 语句
除了 @if,还可以使用 @else if 和 @else 来添加更多的条件分支。
$button-size: medium;
.button {
@if $button-size == small {
padding: 5px 10px;
} @else if $button-size == medium {
padding: 10px 25px;
} @else if $button-size == large {
padding: 15px 30px;
} @else {
padding: 10px 20px; // 默认值
}
}
在这个例子中,根据 $button-size 变量的值,会选择不同的 padding 值应用于 .button 类。如果没有匹配的条件,则会执行 @else 中的代码块。
条件语句的嵌套
条件语句也可以嵌套使用,以处理更复杂的逻辑。
$button-style: flat;
$button-size: medium;
.button {
@if $button-style == flat {
background-color: transparent;
color: #333;
border: 1px solid #333;
@if $button-size == small {
padding: 5px 10px;
} @else if $button-size == medium {
padding: 10px 25px;
} @else if $button-size == large {
padding: 15px 30px;
} @else {
padding: 10px 20px; // 默认值
}
} @else if $button-style == raised {
background-color: #3498db;
color: #fff;
padding: 10px 20px;
border-radius: 4px;
} @else {
// 默认样式
background-color: #db6334;
color: #fff;
padding: 10px 20px;
}
}
在这个例子中,根据 $button-style 和 $button-size 的值,选择不同的样式进行应用。这种嵌套的方式使得可以根据多个条件生成复杂的样式规则。
结论
通过使用条件语句,可以在 SCSS 中实现更加灵活和动态的样式定义,根据不同的条件生成不同的 CSS 规则,从而提高了样式表的可维护性和扩展性。
SCSS中的三种循环
在 SCSS 中,可以使用三种主要的循环结构来生成重复的 CSS 规则,这些循环结构包括 @for、@each 和 @while。
@for 循环
@for 循环用于按照一定的步长和条件重复生成样式。
基本语法:
@for $i from <start> through <end> {
// 循环体
}
- from <start> through <end>:指定循环的起始值和结束值(包括结束值)。
- 循环体中可以使用 $i 变量来表示当前循环的索引值。
示例:
@for $i from 1 through 3 {
.item-#{$i} {
width: 100px * $i;
}
}
在上面的例子中,生成了三个类 .item-1、.item-2 和 .item-3,分别设置宽度为 100px、200px 和 300px。
@each 循环
@each 循环用于遍历列表或者 map 类型的数据,并针对每个元素生成样式。
基本语法:
@each $var in <list or map> {
// 循环体
}
- $var:代表当前循环的变量。
- <list or map>:可以是一个列表(如 $list: item1, item2, item3;)或者一个 map(键值对)。
示例:
$colors: (red, green, blue);
@each $color in $colors {
.text-#{$color} {
color: $color;
}
}
在这个例子中,生成了三个类 .text-red、.text-green 和 .text-blue,分别设置它们的文字颜色为对应的颜色值。
@while 循环
@while 循环根据一个条件来重复生成样式,直到条件不满足为止。
基本语法:
$i: 1;
@while $i < 4 {
// 循环体
$i: $i + 1; // 更新条件
}
- $i:作为循环计数器或者条件变量。
- 循环体中可以执行任意 SCSS 代码,通常在循环体末尾需要更新条件变量,避免无限循环。
示例:
$i: 1;
@while $i < 4 {
.item-#{$i} {
width: 100px * $i;
}
$i: $i + 1;
}
这段代码生成了三个类 .item-1、.item-2 和 .item-3,分别设置它们的宽度为 100px、200px 和 300px。
总结
SCSS 的三种循环结构 @for、@each 和 @while 分别用于按照索引循环、遍历列表或 map 类型数据、以及根据条件循环生成样式。这些循环结构使得 SCSS 更加强大和灵活,能够根据需求生成复杂的 CSS 规则。
自定义函数及使用
在 SCSS 中,可以使用自定义函数来增强样式表的功能,这些函数可以接受参数并返回处理后的值。
定义自定义函数
在 SCSS 中,使用 @function 关键字来定义函数,函数可以有参数和返回值。例如,我们定义一个函数来计算一个元素的盒子模型总宽度:
@function total-width($padding, $border, $margin, $content-width) {
@return $padding + $border + $margin + $content-width;
}
在上面的例子中:
- total-width 是函数的名称。
- 函数接受四个参数:$padding、$border、$margin、$content-width。
- @return 语句用于返回计算后的值。
使用自定义函数
一旦定义了函数,就可以在样式中使用它来计算和生成需要的值。例如:
.element {
width: total-width(10px, 1px, 5px, 100px);
}
在这个例子中,total-width 函数会被调用,参数分别是 10px、1px、5px 和 100px。函数返回的结果(116px)将被应用到 .element 的宽度属性中。
注意事项
- 函数可以包含在任何 SCSS 文件中,并且可以像其他样式规则一样进行组织和导入。
- 函数中可以使用 SCSS 的所有功能,例如控制语句(如 @if、@for、@each、@while)和内置函数。
- 函数的参数可以是任意 SCSS 数据类型,包括数字、字符串、颜色等。
课后练习
使用SCSS 实现页面的黑白色主题切换
html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" href="main.css">
<title>黑白色主题切换</title>
</head>
<body>
<div class="container">
<button id="theme-toggle">切换主题</button>
<div class="box">
<div class="content">
<p>这是一些文本内容。</p>
<p>这是一些文本内容。</p>
<p>这是一些文本内容。</p>
<p>这是一些文本内容。</p>
<p>这是一些文本内容。</p>
<p>这是一些文本内容。</p>
<p>这是一些文本内容。</p>
</div>
</div>
</div>
<script src="main.js"></script>
</body>
</html>
scss
// 定义轻主题的样式变量
$light-theme: (
background-color: white,
text-color: black,
highlight-color: #f0f0f0
);
// 定义暗主题的样式变量
$dark-theme: (
background-color: black,
text-color: white,
highlight-color: #333333
);
// 定义一个混合(mixin)来应用主题样式
// 参数 $theme: 要应用的主题,是一个包含背景色、文本颜色和高亮颜色的映射(map)
@mixin theme($theme) {
background-color: map-get($theme, background-color);
color: map-get($theme, text-color);
// 为 .box 类应用主题的高亮颜色
.box {
background-color: map-get($theme, highlight-color);
}
}
// 应用轻主题样式到 body 元素,并添加过渡效果
body {
@include theme($light-theme);
transition: all 0.3s ease;
}
// 为 body 的 dark 类应用暗主题样式
body.dark {
@include theme($dark-theme);
}
// 设置容器的文本居中和顶部间距
.container {
text-align: center;
margin-top: 20px;
}
// 配置主题切换按钮的样式
#theme-toggle {
padding: 10px 20px;
cursor: pointer;
border: none;
outline: none;
background-color: #007bff;
color: white;
font-size: 16px;
border-radius: 5px;
}
// 鼠标悬停在主题切换按钮上时改变背景色
#theme-toggle:hover {
background-color: #0056b3;
}
// 定义 .box 类的基本样式和过渡效果
.box {
margin: 20px auto;
padding: 20px;
width: 50%;
border: 1px solid #ccc;
transition: all 0.3s ease;
// 内容区域的样式配置
.content {
p {
margin: 10px 0;
}
}
}
js
/**
* 为主题切换按钮添加点击事件监听器
* 当按钮被点击时,切换文档主体的黑暗主题样式
*
* 该函数通过toggle方法动态切换body元素的'dark'类,从而实现主题的切换。
* 如果body已经应用了'dark'类,那么点击按钮将移除这个类,反之亦然。
* 这种方式允许用户在黑暗主题和默认主题之间自由切换。
*/
document.getElementById('theme-toggle').addEventListener('click', () => {
document.body.classList.toggle('dark');
});