SASS -跨多个文件使用变量

我想保留一个中心的.scss文件,用于存储项目的所有SASS变量定义。

// _master.scss


$accent: #6D87A7;
$error: #811702;
$warning: #F9E055;
$valid: #038144;
// etc...

该项目将有大量的CSS文件,由于其性质。在一个位置声明所有项目范围的样式变量是很重要的。

在SCSS中有办法做到这一点吗?

277958 次浏览

你可以这样做:

我有一个名为utilities的文件夹,其中有一个名为_variables.scss的文件

在这个文件中,我像这样声明变量:

$black: #000;
$white: #fff;

那我就有风格了。我导入了所有其他SCSS文件,如下所示:

// Utilities
@import "utilities/variables";


// Base Rules
@import "base/normalize";
@import "base/global";

然后,在我导入的任何文件中,我都应该能够访问我已经声明的变量。

只需要确保在导入其他变量文件之前导入该变量文件。

这个答案显示了我最终是如何使用它的,以及我遇到的额外陷阱。

我做了一个主SCSS文件。这个文件必须的开头有一个下划线,用于导入它:

// assets/_master.scss
$accent: #6D87A7;
$error: #811702;

然后,在我所有其他.SCSS文件的头文件中,我导入了主文件:

// When importing the master, you leave out the underscore, and it
// will look for a file with the underscore. This prevents the SCSS
// compiler from generating a CSS file from it.
@import "assets/master";


// Then do the rest of my CSS afterwards:
.text { color: $accent; }

重要的

_master.scss文件中除了变量、函数声明和其他SASS特性外,不要包含任何东西。如果您包含实际的CSS,它将在导入主文件的每个文件中复制此CSS。

创建索引。SCSS,在那里你可以导入所有的文件结构。我将粘贴你我的索引从一个企业项目,也许它将帮助其他如何在css结构文件:

@import 'base/_reset';


@import 'helpers/_variables';
@import 'helpers/_mixins';
@import 'helpers/_functions';
@import 'helpers/_helpers';
@import 'helpers/_placeholders';


@import 'base/_typography';


@import 'pages/_versions';
@import 'pages/_recording';
@import 'pages/_lists';
@import 'pages/_global';


@import 'forms/_buttons';
@import 'forms/_inputs';
@import 'forms/_validators';
@import 'forms/_fieldsets';


@import 'sections/_header';
@import 'sections/_navigation';
@import 'sections/_sidebar-a';
@import 'sections/_sidebar-b';
@import 'sections/_footer';


@import 'vendors/_ui-grid';


@import 'components/_modals';
@import 'components/_tooltip';
@import 'components/_tables';
@import 'components/_datepickers';

你可以用gulp/grunt/webpack等方式观看,比如:

gulpfile.js

// SASS任务

var gulp = require('gulp');
var sass = require('gulp-sass');
//var concat = require('gulp-concat');
var uglifycss = require('gulp-uglifycss');
var sourcemaps = require('gulp-sourcemaps');


gulp.task('styles', function(){
return gulp
.src('sass/**/*.scss')
.pipe(sourcemaps.init())
.pipe(sass().on('error', sass.logError))
.pipe(concat('styles.css'))
.pipe(uglifycss({
"maxLineLen": 80,
"uglyComments": true
}))
.pipe(sourcemaps.write('.'))
.pipe(gulp.dest('./build/css/'));
});


gulp.task('watch', function () {
gulp.watch('sass/**/*.scss', ['styles']);
});


gulp.task('default', ['watch']);

在全局sass文件中编写一些基于颜色的类如何,这样我们就不需要关心变量在哪里了。就像下面这样:

// base.scss
@import "./_variables.scss";


.background-color{
background: $bg-color;
}

然后,我们可以在任何文件中使用background-color类。 我的观点是,我不需要在任何文件中导入variable.scss,只需使用它。< / p >

这个问题很久以前就有人问过了,所以我想我应该更新一下答案。

你现在应该使用@import避免。摘自以下文件:

Sass将在未来几年内逐步淘汰它,并且 最终将其从语言中完全移除。更喜欢@use规则 相反。< / p >

完整的原因列表可以在这里找到

你现在应该使用@use,如下所示:

_variables.scss

$text-colour: #262626;

_otherFile.scss

@use 'variables'; // Path to _variables.scss Notice how we don't include the underscore or file extension


body {
// namespace.$variable-name
// namespace is just the last component of its URL without a file extension
color: variables.$text-colour;
}

你也可以为命名空间创建一个别名:

_otherFile.scss

@use 'variables' as v;


body {
// alias.$variable-name
color: v.$text-colour;
}

正如@und3rdg在撰写本文时(2020年11月)指出的那样,@use目前仅适用于Dart Sass和 LibSass(现已弃用)或Ruby Sass。有关最新兼容性,请参阅https://sass-lang.com/documentation/at-rules/use

在angular v10中,我做了类似的事情,首先创建一个master.scss文件,并包含以下变量:

master.scss文件:


$theme: blue;


$button_color: red;


$label_color: gray;

然后我导入了master.scss文件在我的style.scss的顶部:

风格。scss文件:

@use './master' as m;

确保在顶部导入master.scss

m是命名空间的别名;

根据下面的官方文档,使用@use而不是@import:

https://sass-lang.com/documentation/at-rules/import

然后在你的styles.scss文件中,你可以使用在master.scss中定义的任何变量,如下所示:

someClass {


backgroud-color: m.$theme;


color: m.$button_color;


}

希望它能有所帮助……

快乐编码:)

如前所述,在新版本的SASS中不鼓励使用@import。在你的文件顶部使用@use "path to SASS partial file"代替

你需要导入(使用@use)部分SASS文件到使用它的每一个 SASS文件中-而不仅仅是你的主文件。

假设我们在名为partials的文件夹中有一个名为_variables.scss*的SASS文件,我们想在header.scss中使用它。所以在header.scss中你写:

@use "partials/variables" as *

现在你可以使用在_variables.scss*中定义的所有变量和$variable(没有前缀)。或者,也可以使用名称空间(如前面提到的Christian)

@use "partials/variables" as v

v.$variable引用_variables.scss*中的变量。

*注意,SASS编译器忽略下划线,因此不会为每个部分SASS文件生成单独的CSS文件。相反,你可以用@use将它们全部导入你的主SASS文件。

我用vite找到了vue3的解决方案。如果你正在使用dart-sass,你可以通过使用@forward@use来绕过sass模块的全局限制。

_master.scss

$accent: #6D87A7;
$error: #811702;
$warning: #F9E055;
$valid: #038144;
// etc...

_global.scss

@forward '_master.scss';
// etc...

然后在vite.config.js下配置css选项为

export default defineConfig({
css: {
preprocessorOptions: {
scss: {
additionalData: `
@use "./<path-to-file>/_globals.scss" as *;
`,
},
},
},
// etc...
});

正如在sass文档中提到的,当导入没有命名空间的模块时

不过,我们建议只对自己编写的样式表这样做;否则,他们可能会引入新成员,导致名称冲突!

然后,您可以在任何其他样式表或组件中使用其他@use模块,如下所示

// component file needing a function module


@use 'functions.scss';