SASS 模块
本文介绍 SASS 模块。
我们将介绍如何使用 @use 和 @forward 实现 SASS 模块化,以及如何复用变量、混合宏、函数、主题设置和公共 API。
YouTube Video
SASS 模块
SASS 的模块系统可以清晰地限定样式的作用域,并提供易于复用和维护的设计。
模块的基本概念
SASS 模块解决了旧版 @import 出现的全局命名空间污染和依赖不明确的问题。每个文件作为模块加载,都拥有自己的命名空间,只有明确导出的内容可以被其他文件访问。
示例文件结构
首先,以下是一个实际项目结构的例子:。下面是一个小型设计系统的示例。
1styles/
2├─ _variables.scss
3├─ _mixins.scss
4├─ _functions.scss
5├─ components/
6│ ├─ _button.scss
7│ └─ _card.scss
8├─ utilities/
9│ └─ _helpers.scss
10└─ main.scss- 这种结构不仅便于模块化,还便于测试与替换某些部分。
- 片段文件的文件名前缀一般为下划线(_)。
@use的基础用法
@use用于加载模块并提供命名空间。这样可以避免命名冲突,并明确变量和函数的来源模块。
1// _variables.scss
2$primary-color: #0a74da;
3$padding-base: 12px;- 该文件只是简单地定义了一些变量。通过
@use,可以直接引用模块公开的变量。
1// main.scss
2@use 'variables';
3
4.example {
5 color: variables.$primary-color;
6 padding: variables.$padding-base;
7}- 这里使用
variables.命名空间来引用variables模块。这种方式可以清楚地了解每个变量或函数的来源。
命名空间简写与别名
使用as可以缩短命名空间。
1@use 'variables' as vars;
2
3.btn {
4 color: vars.$primary-color;
5}- 下面是使用
vars作为variables模块简称的导入示例。根据你是更注重可读性还是输入的便捷性,选择合适的命名。
混合宏定义
mixin和函数也可以在模块内定义并使用。注释风格与项目规范一致,有助于提高代码清晰度。
1// _mixins.scss
2// Create a simple responsive container mixin
3@mixin container($max-width: 1200px) {
4 width: 100%;
5 margin-left: auto;
6 margin-right: auto;
7 max-width: $max-width;
8}- 此文件定义了一个容器的mixin。它可以接受参数并设置默认值。
1// main.scss
2@use 'mixins' as m;
3
4.wrapper {
5 @include m.container(1000px);
6}- 以下是用
@include调用mixin的示例。
函数定义
函数用于返回值,并可在模块内定义和复用。通过将设计值的计算封装进函数,样式会更加稳定且易于维护。
1// _functions.scss
2@use 'sass:math';
3
4// Create a simple px-to-rem converter function
5@function to-rem($px, $base: 16) {
6 @return math.div($px, $base) * 1rem;
7}- 此文件定义了一个将像素值转换为 rem 的函数。还指定了一个默认基准值。
1// main.scss
2@use 'functions' as f;
3
4.title {
5 font-size: f.to-rem(24);
6}- 下面是通过
@use调用函数并将结果应用于样式的示例。
模块导出与@forward(API设计)
如果需要对外公开多个内部文件,可以用@forward创建“公共API”。
1// _index.scss (module entry)
2@forward 'variables';
3@forward 'mixins';
4@forward 'functions';- 多个内部文件可以汇集在一个入口文件,通过该入口对外提供公共API。这样使用者只需导入这个入口文件即可访问所有需要的功能。
1// main.scss
2@use 'index' as ds; // ds = design system
3
4.button {
5 color: ds.$primary-color;
6 @include ds.container();
7}variables和mixins的内容可以通过index一并访问。@forward使index成为公共层。
用@forward的show/hide选项控制API
如果只想公开特定变量,可以使用show或hide选项。
1// _variables.scss
2$internal-thing: 10px !default; // for internal use
3$primary-color: #0a74da !default;
4$secondary-color: #f5f5f5 !default;- 使用
!default可以让变量值支持被外部覆盖。
1// _index.scss
2@forward 'variables' show $primary-color, $secondary-color;
3@forward 'mixins';- 通过
@forward的show限定,可以只暴露必要的API元素。内部使用的变量和函数不会对外部可见。
让模块支持配置(使用with)
如果模块中的变量使用了!default,则可以在导入时用with覆盖。
1// _theme.scss
2$brand-color: #ff6600 !default;
3$radius: 4px !default;
4
5@mixin button-style() {
6 background-color: $brand-color;
7 border-radius: $radius;
8}- 用
!default定义默认值的模块,可以通过with来接受配置。
1// main.scss
2@use 'theme' with (
3 $brand-color: #2288ff,
4 $radius: 8px
5);
6
7.my-btn {
8 @include theme.button-style();
9}@use ... with语法可在导入时覆盖模块中的默认变量。这对于主题切换非常有用。- 注意,
with只在导入时生效,之后不能再修改这些值。
实用例子:按钮组件(完整示例)
下面我们试着用模块来设计按钮样式。首先,将变量和mixin分别放入单独的模块。
1// _variables.scss
2$btn-padding-y: 8px !default;
3$btn-padding-x: 16px !default;
4$btn-font-size: 14px !default;
5$btn-primary-bg: #0a74da !default;
6$btn-primary-color: #fff !default;- 这里定义了按钮的默认变量。使用
!default可以让使用者自定义这些默认值。
1// _mixins.scss
2@use "variables" as v;
3
4@mixin btn-base() {
5 display: inline-flex;
6 align-items: center;
7 justify-content: center;
8 padding: v.$btn-padding-y v.$btn-padding-x;
9 font-size: v.$btn-font-size;
10 border: none;
11 cursor: pointer;
12}- 这里定义了按钮的基础mixin。这样分离便于复用。
1// _button.scss
2@use 'variables' as v;
3@use 'mixins' as m;
4
5.button {
6 @include m.btn-base();
7 background: v.$btn-primary-bg;
8 color: v.$btn-primary-color;
9 border-radius: 4px;
10 transition: opacity 0.15s ease;
11 &:hover { opacity: 0.9; }
12}
13
14.button--large {
15 padding: calc(v.$btn-padding-y * 1.5) calc(v.$btn-padding-x * 1.5);
16 font-size: v.$btn-font-size * 1.25;
17}- 按钮样式通过
@use命名空间引用创建。有一个变体类,如.button--large。
1// main.scss
2@use 'button'; // or @use 'index' that forwards button, variables, mixins- 只需导入
button模块,即可直接应用按钮样式。
主题切换(使用多个主题文件)
主题切换可以通过with配置,也可以创建多个主题模块,根据需要用@use切换。
1// themes/_light.scss
2$brand-color: #0a74da !default;1// themes/_dark.scss
2$brand-color: #111827 !default;- 可以在多个主题文件中定义品牌色等设置,在构建或导入时切换使用。
1// main.scss (light theme)
2@use 'theme' with ($brand-color: #0a74da);
3@use 'button';- 选择主题时,可以用
with,也可以如@use 'themes/light'那样在构建时指定导入主题。
私有与公共(下划线前缀和!default)
在 SASS 中,文件名开头加下划线会被标记为部分样式(partial)。但要管理模块导出可见性,建议用@forward的show和hide选项。
利用@forward可以整理公共API,隐藏内部实现。
实际项目中的最佳实践
以下是在实际使用 SASS 时非常有用的一些基本概念。这些准则都有助于减少开发中的混乱,保持代码结构清晰。
- 如果变量可能因主题变化而改变,请加上
!default。这样用户更容易覆盖其数值。 - 模块应按责任进行划分,每个模块聚焦单一目标。通过将变量、混合宏、组件分离后,更便于管理。
- 通过
@forward管理公共内容,必要时结合show和hide。严格定义公共内容范围有助于实现更安全的设计。 - 通过命名空间,明确每个函数属于哪个模块。这样可以避免与其他代码混淆。
- 请注意,
with仅在@use时生效。因导入后不可再更改配置,请在导入时指定。 - 文件名前加下划线,使其为片段文件,不会单独编译。这样更易于将文件组合成更大的结构。
index模块中包含用例有助于测试与文档说明。这样用户更容易理解其行为。
牢记这些要点,有助于管理大型项目,同时保持团队代码可读性。
总结
SASS 模块系统通过命名空间、公共 API 和简化的配置来组织样式代码。熟练使用@use和@forward,能显著提升团队开发、主题切换和库设计的效率。
您可以在我们的YouTube频道上使用Visual Studio Code跟随上述文章进行学习。 请也查看我们的YouTube频道。