15

我环顾四周,看到了一个解决方案,在您的 html 中,您有一个专用于将 sass 变量传递给 javascript 的标签。我说的是第二个答案

有没有办法将变量从 javascript 导入 sass,反之亦然?

我也尝试过使用 html

<div class="selector"></div>

用CSS

.selector { content: "stuff"; }

但是查看开发人员工具中的 dom,即使我们可以在呈现的页面上看到它,它也没有被添加,所以我无法使用 javascript 来获取它

$('.selector').text()

大家是怎么做的?

4

4 回答 4

10

不确定“行业标准”,但这是一种非常方便的技术,而且不太难。但是,伪元素的内容不能通过text(),您必须使用getComputedStyle.

使用示例body:after

Sass(使用罗盘断点扩展):

body:after {
  display: none;

  @include breakpoint($bp-wide) {
    content: "wide";
  }

  @include breakpoint($bp-medium) {
    content: "medium";
  }

  @include breakpoint($bp-small) {
    content: "small";
  }
}

JavaScript

if (window.getComputedStyle) {
  var mq = window.getComputedStyle(document.body,':after').getPropertyValue('content');
}

if (mq.indexOf('small') !== -1) {
  // do something
}

信用:我在这里第一次看到这种技术:https ://coderwall.com/p/_ldtkg

于 2013-08-27T05:32:39.280 回答
4

我相信通过 CSScontent属性注入 SASS 变量是一种非常骇人听闻的做事方式。

相反,您可以将变量存储在单独的位置,并让 SASS 和 JS 读取它们。

首先,将断点列表存储在breakpoints.json文件中:

["0", "300px", "500px", "700px", "900px", "1100px"]

然后使用 Ruby 读取这个 JSON 文件,并通过 SASS 函数将其内容作为 SASS 列表提供。把它放进你的指南针config.rb

sass_options = { :custom => {'breakpoint_file' => 'breakpoints.json'} }

# This creates a SASS function debug() that returns $debug into SASS
module Sass::Script::Functions
  def breakpoints

    # Reading an array of breakpoints into a file
    unless breakpoints_array_raw = JSON.load( IO.read( options[:custom]['breakpoint_file'] ))
      raise Sass::SyntaxError.new("Error: Breakpoints file '#{options[:custom]['breakpoint_file']}' does not exist.")
    end

    # Converting strings in the array to SASS String literals
    breakpoints_array_sassy = breakpoints_array_raw.map { |s| Sass::Script::String.new(s) }

    # Returning the list into SASS
    Sass::Script::List.new( breakpoints_array_sassy, :space )
  end
end

在您的 SASS 代码中,读取如下断点:

$breakpoints: breakpoints()

在 JS 中,使用 jQuery 的.get方法来请求 JSON 文件,如下所示:

var
  breakpoints = [],
  requestBreakpoints = $.get('breakpoints.json');

requestBreakpoints.done(function (response, textStatus, jqXHR){
    breakpoints = response; // You might want to remove "px" here
});

当我组装这个设置时,我在这里找到了一个现有的解决方案,但我决定使用我最喜欢的 SASS 工具重新实现它:SingularityBreakpoint Slicer

为了您的方便,我构建了一个概念验证GitHub 项目,所有内容都设置得很好,其中包含一些丑陋的 JS 代码。:)

这是一个现场演示

于 2013-08-27T10:24:13.343 回答
2

通过 CSScontent属性共享状态似乎很脏。我也不喜欢提出额外的 XHR 请求的想法。

我想构建一个自定义解决方案,只编译 SASS 文件和 JS 模块。但事实证明,有一个npm名为rosetta的包。它正是这样做的。输出格式非常灵活,我很快就将其设置为一项Grunt.js任务。

$ npm install rosetta

这是示例Gruntfile.js

module.exports = function(grunt) {

  // Project configuration.
  grunt.initConfig({
    pkg: grunt.file.readJSON('package.json'),
      watch: {
          css: {
              files: ['sass/*.scss', 'sass/lib/*.scss', 'rosetta/*.rose'],
              tasks: ['rosetta', 'compass']
          }
      },
      compass: {
          dist: {
              options: {
                  sassDir: 'sass',
                  cssDir: '../static/css',
                  imagesDir: '../static/img',
                  javascriptsDir: '../static/js'
              }
          }
      },
      rosetta: {
          default: {
             src: ['rosetta/*.rose'],
             options: {
                 jsFormat: 'requirejs',
                 cssFormat: 'scss',
                 jsOut: '../static/js/lib/rosetta.js',
                 cssOut: 'sass/_shared_variables.scss'
             }
          }
      }
  });

  grunt.loadNpmTasks('grunt-contrib-watch');
  grunt.loadNpmTasks('grunt-contrib-compass');
  grunt.loadNpmTasks('rosetta');
  grunt.registerTask('default', ['watch']);

};

package.json

{
  "name": "",
  "version": "0.0.0",
  "description": "",
  "main": "Gruntfile.js",
  "dependencies": {
    "grunt": "^0.4.5",
    "grunt-cli": "^0.1.13",
    "grunt-contrib-compass": "^0.9.1",
    "grunt-contrib-watch": "^0.6.1",
    "rosetta": "git+https://github.com/ukolka/rosetta.git"
  },
  "devDependencies": {},
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "",
  "license": "ISC"
}

毕竟你只需要在 SASS中导入_shared_variables.scss并在你的 JavaScript 中使用rosetta.js模块来访问公共变量。当您更改 *.rose 文件时,您的样式和 JS 将被更新。

于 2014-08-26T17:16:43.860 回答
1

如果您正在使用GULPGRUNT(我希望您使用的是第一个)

这个例子展示了如何使用gulp

在 gulpfile 或另一个文件中定义颜色,然后将其导入您的 gulpfile,然后您可以SCSS像这样动态构建变量和 javascript:

variables_template.scss(不要在你的主 scss 文件中导入)

...
$colors : ([COLORS])
...

app.js(一些包含颜色变量的 js 文件)

var appColors = {[COLORS]};

gulpfile.js

var gulp    = require('gulp'),
    gutil   = require('gulp-util'),
    replace = require('gulp-replace');

var appColors = {
   "red"   : "#d63737",
   "green" : "#69c962"
};

gulp.task('scssVars', ()=>{
    var colorsString = JSON.stringify(appColors);
    colorsString  = colorsString.slice(2,colorsString.length - 2);

    return gulp.src('css/variables_template.scss')
        .pipe(replace(/[COLORS]/g, colorsString ))
        .pipe(rename('variables.scss'))
        .pipe(gulp.dest('/'))
});

// do more of less the same for your app.js, only without renaming, if possible

SCSS 变量的类似 NPM gulp 包:

于 2017-02-22T14:44:10.357 回答