有时有必要设置一些常量两次:在 SASS 和 JS 中(例如为了更好的性能)。有谁知道同步 SASS/SCSS 和 JavaScript 变量以从 JavaScript 或从 SASS 到 JavaScript 访问 SCSS 变量的解决方案?
最佳答案
我知道大约一年前有人问过这个问题,但我把这个答案作为下一个遇到这个问题的可怜人的引用。可能有更好的解决方案,但这是我唯一能找到/想出的解决方案。
由于 JavaScript 似乎无法直接从任何 .scss
文件中获取变量,因此我们必须使用正则表达式从我们的文件中获取所需的值。但是因为我们不想让它搜索整个 SASS 文件:
创建一个包含变量的 SASS 文件
我们创建一个新文件 _variables.scss
,供 JavaScript 搜索。假设它看起来像这样:
$menuMobileArrowRotate: 90;
$articleScale: 1.1;
将其导入我们的主 SASS 文件
通过在样式表顶部附近添加 @import "variables";
将其导入 SASS。然后我们可以在整个文件中使用这些变量,而不是手动输入值。
将其导入 JavaScript
我要让 JavaScript 读取 _variables.scss
并将其转换为字符串:
var sassVariables = new XMLHttpRequest();
sassVariables.open("GET", 'http://www.use-absolute-url.com/_variables.scss', false);
sassVariables.send(null);
注意:要支持 IE6 及更早版本,请将 var xmlhttp = new XMLHttpRequest();
替换为:
if (window.XMLHttpRequest) {
var sassVariables = new XMLHttpRequest();
}
else {
var sassVariables = new ActiveXObject("Microsoft.XMLHTTP");
}
如果我设置异步。为 true
,Firebug 向我显示一个错误,声称 fileContent
不存在。由于我的文件只有 4KB,因此我不会因为必须等待它加载而过分担心潜在的性能问题。
现在,我要声明我的变量:
var fileContent = sassVariables.responseText, //a string holding the contents of my file
menuMobileArrowRotate = null,
articleScale = null;
我在确定文件实际加载之前声明了 menuMobileArrowRotate
和 articleScale
,因为我不希望 JavaScript 给我一个错误并把一切都搞砸,因为它没有加载。
如果一切加载正常,我将使用 RegEx 找出每个变量的值。至少我只浏览了一个小文件,而不是搜索整个样式表。
if (sassVariables.status === 200) { //if everything loaded nice and dandy
menuMobileArrowRotate = fileContent.match(/(?:menuMobileArrowRotate.\s*?)(\d+)/)[1];
articleScale = data.match(/(?:articleScale.\s*?)((\d+)\.*(\d+)*)/)[1];
}
注意 .match()
之后的 [1]
:RegEx 返回一个数组,我只想要第一个匹配项(在我的例子中,也是仅匹配)。
对于所有的 JS 放在一起:
if (window.XMLHttpRequest) {
var sassVariables = new XMLHttpRequest();
}
else {
var sassVariables = new ActiveXObject("Microsoft.XMLHTTP");
}
sassVariables.open("GET", 'http://mysite.com/sass/_variables.scss', false);
sassVariables.send(null);
var fileContent = sassVariables.responseText,
menuMobileArrowRotate = null,
articleScale = null;
if (sassVariables.status === 200) {
menuMobileArrowRotate = fileContent.match(/(?:menuMobileArrowRotate.\s*?)(\d+)/)[1];
articleScale = fileContent.match(/(?:articleScale.\s*?)((\d+)\.*(\d+)*)/)[1];
}
console.log(menuMobileArrowRotate); //shows 90
console.log(articleScale); //shows 1.1
我现在可以按照这段代码在我的 JavaScript 文件中的任何位置使用这些变量。
奖励:媒体查询变量
SASS 不允许您在媒体查询中 使用变量。但是,我可以make the whole dang query a mixin , 并将其放入 _variables.scss
:
@mixin mediaQuery($point) {
@if $point == 'mobile' {
@media only screen and (max-width: 600px) { @content; }
}
@if $point == 'somethingElse' {
@media only screen and (max-width: 1000px) { @content; }
}
}
在 style.scss
中,我可以:
@include mediaQuery(mobile) {
//blah
}
@include mediaQuery(somethingElse) {
//blah
}
然后我可以使用相同的过程来获得所需的值(即 600 和 1000),只是使用不同的 RegEx。
关于javascript - 如何在同一个地方设置 JavaScript 和 SASS 常量?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12582157/