/** * * @author yutent * @date 2018/11/01 09:37:55 */ 'use strict' const vsc = require('vscode') const path = require('path') const fs = require('iofs') const ScssLib = require('./lib/index.js') const postcss = require('postcss') const autoprefixer = require('autoprefixer') let prefixer const log = console.log const render = function(style, file) { return new Promise((resolve, reject) => { ScssLib(file, { style: ScssLib.Sass.style[style] }, res => { if (res && res.text) { resolve(res.text) } else { reject(res) } }) }) } let options = { compileOnSave: true, autoPrefixer: true, output: 'compressed', exclude: '' } const compileCss = (style, entry, output) => { if (options.outdir) { let tmp = output.replace(options.workspace, '.') output = path.join(options.outdir, tmp) } return render(style, entry).then(css => { if (options.autoPrefixer) { return prefixer.process(css, { from: '', to: '' }).then(result => { return { css: result.css, output } }) } else { return { css, output } } }) } const Compiler = { compile(doc) { let origin = doc.fileName || '' let target = origin.replace(/\.scss$/, '') let task = [] // 说明不是scss文件 if (origin === target) { return } task = options.output.map(style => { let ext = '.css' switch (style) { case 'compressed': ext = '.min' + ext break default: ext = style.slice(0, 1) + ext } return { style, output: target + ext } }) // 编译单一类型, 则去掉文件名微调 if (task.length === 1) { task[0].output = target + '.css' } task = task.map(item => { return compileCss(item.style, origin, item.output) }) Promise.all(task) .then(list => { list.forEach(it => { fs.echo(it.css, it.output) }) }) .catch(err => { vsc.window.showInformationMessage(err) }) }, /** * 条件过滤 * 用于保存时编译的动作, 右键编译时, 不过滤这2项 */ filter(doc) { // 未开启保存时编译 if (!options.compileOnSave) { return } let origin = doc.fileName || '' // var.scss文件默认不编译 if (/\/var\.scss$/.test(origin)) { return } // 过滤不编译的文件 if (options.exclude) { let exp = new RegExp(options.exclude, 'i') if (exp.test(origin)) { return } } this.compile(doc) } } function __init__() { let conf = vsc.workspace.getConfiguration('Scss2css') let folders = vsc.workspace.workspaceFolders let wsDir = '' let configFile = '' Object.assign(options, conf) conf = null options.output = options.output.split('|').map(it => it.trim()) if (folders && folders.length) { wsDir = folders[0].uri.path } if (wsDir) { configFile = path.join(wsDir, '.scssrc') } else { let editor = vsc.window.activeTextEditor if (editor) { wsDir = path.dirname(editor.document.fileName) configFile = path.join(wsDir, '.scssrc') } } // 以配置文件所在目录为根目录(workspace) if (fs.exists(configFile)) { options.workspace = path.dirname(configFile) let tmp = JSON.parse(fs.cat(configFile).toString()) Object.assign(options, tmp) tmp = null if (options.outdir) { options.outdir = path.join(options.workspace, options.outdir) } } prefixer = postcss().use( autoprefixer({ browsers: options.browsers }) ) } function activate(ctx) { __init__() vsc.workspace.onDidChangeConfiguration(__init__) vsc.workspace.onDidSaveTextDocument(doc => { Compiler.filter(doc) }) let cmd = vsc.commands.registerCommand('Scss2css.compile', _ => { let editor = vsc.window.activeTextEditor if (editor) { Compiler.compile(editor.document) } }) ctx.subscriptions.push(cmd) } function deactivate() {} exports.activate = activate exports.deactivate = deactivate