Open toFrankie opened 1 year ago
在使用 VS Code 编写代码时,通常会开启 editor.formatOnSave 选项以在保存时格式化文件。
editor.formatOnSave
{ "editor.formatOnSave": true }
一般来说,对于大多数语言来说,VS Code 都有对应的内置格式化程序(formatter)。它们通常只会处理缩进、折行、前导尾随空格等操作。
如果内置的不够用,可以通过安装第三方插件以实现更多的可能。比如,将颜色值转为小写、改进 JavaScript 写法等都可以在保存文件时自动处理,具体取决于插件实现。
由于语言众多,格式化插件也很多,还可以支持配置默认的格式化程序。这个可以在文件编辑区右键选择「使用 ... 格式化」进行配置。比如:
{ "[html]": { "editor.defaultFormatter": "vscode.html-language-features" }, "[css]": { "editor.defaultFormatter": "stylelint.vscode-stylelint" }, "[javascript]": { "editor.defaultFormatter": "esbenp.prettier-vscode" } }
现在很多工程化项目都会配置格式化处理,也可在 Git 的 pre-commit 勾子中跑一遍处理脚本,以确保提交到仓库的代码格式是统一的,尽管大家使用的编辑器可能有差异。
pre-commit
虽说如此,仍然有必要我们的编辑器配置一些格式化程序,以便于在编写一些 Snippet、Demo 等的时候,也有着较为规范、格式统一的代码。尤其是像我这种强迫症患者。
个人用得最多的是 Prettier,主流编辑器都有对应插件,支持 JavaScript、HTML、CSS 以及对应变体等 Web 前端相关的语言。
Prettier 是固执己见的(opinionated),提供的选项很少,且在可见的未来可能不会添加更多新功能。原因请看 Option Philosophy。
目前我想要的是:在保存文件时,按一定的规则自动对 CSS 属性进行排序。此时 Prettier 就无能为力了。
对于 CSS 属性声明顺序,最初是因为看了 Code Guide by @AlloyTeam 的规范,目前里面提及的属性顺序已过时,最后维护时间已经是 2015 年了。有一句话我很喜欢(源自):
虽然这些细节是小事,不会有体验或者性能上的优化,但是却体现了一个 coder 和团队的专业程度。
排序的好处无非就是快速看得出元素盒子所占的空间,是否有重复声明的属性等。
目前,本人所参考的是 Code Guide @mdo 规范,对应的 Stylelint 插件是 Bootstrap 在用的 stylelint-config-recess-order,维护较为积极,也能紧跟最新的 CSS 属性,它们会按照以下分组排序(详见):
stylelint-config-recess-order
与 Declaration order 相关的插件还有以下几个,有些已经好几年没更新了,仅供参考。
stylelint-config-rational-order
以上这些集成到项目里面是非常好用的,但对于单个文件或者工程化程度不高的项目,它们没办法施展才华。原因是它们都是基于 Stylelint 的插件 stylelint-order 实现的,而对应 VS Code 插件并不支持配置插件。
stylelint-order
因此,本文会借助一个名为 CSScomb.js 的格式化程序,它的主要功能便是「属性排序」,对应的 VS Code 插件是 vscode-csscomb。
CSScomb.js 最后更新已经是 2019 年,看起来似乎不再维护更新了,对应插件也因此不再更新。
尽管如此,它目前仍然足够好用。
其中 vscode-csscomb 插件配置项有以下几个:
此处不展开说明,具体可看文档:
我的 VS Code 配置如下:
{ "csscomb.formatOnSave": true, "csscomb.syntaxAssociations": { "*.wxss": "css", "*.acss": "css" }, "csscomb.ignoreFilesOnSave": ["node_modules/**"], "csscomb.preset": "~/Library/Mobile Documents/com~apple~CloudDocs/Terminal/csscomb/preset-custom.json", }
其中,对于像小程序等 WXSS 样式文件,可以在 csscomb.syntaxAssociations 进行关联,使其当成 CSS 一样去处理。
csscomb.syntaxAssociations
由于 csscomb.preset 配置项非常地长(sort-order 造成的),也便于多设备同步,我选择将其存放到 iCloud Drive 目录。如下:
csscomb.preset
sort-order
{ "exclude": [ ".git/**", "node_modules/**", "bower_components/**" ], "verbose": true, "always-semicolon": true, "block-indent": 2, "color-case": "lower", "color-shorthand": true, "element-case": "lower", "eof-newline": true, "leading-zero": true, "quotes": "single", "remove-empty-rulesets": false, "space-before-colon": 0, "space-after-colon": 1, "space-before-combinator": 1, "space-after-combinator": 1, "space-before-opening-brace": 1, "space-after-opening-brace": "\n", "space-before-closing-brace": "\n", "space-before-selector-delimiter": 0, "space-after-selector-delimiter": "\n", "space-between-declarations": "\n ", "strip-spaces": true, "unitless-zero": true, "vendor-prefix-align": false, "sort-order": [] }
以上都是一些比较常规的配置,其中一些也是为了跟 Prettier 保持一致而设置的。另外,为了避免影响篇幅以上 sort-order 配置省略了,可参考这里。
由于 CSS 在不断的发展,为了让 sort-order 跟上最新标准,这里使用 stylelint-config-recess-order 来生成。
脚本很简单,仅供参考:
const path = require('path') const fs = require('fs') const propertyGroups = require('stylelint-config-recess-order/groups') const CSSCOMB_SORT_ORDER_FILE_PATH = path.resolve(__dirname, '../csscomb/sort-order.json') const CSSCOMB_PRESET_BASE_FILE_PATH = path.resolve(__dirname, '../csscomb/preset-base.json') const CSSCOMB_PRESET_CUSTOM_FILE_PATH = path.resolve(__dirname, '../csscomb/preset-custom.json') ;(function main() { // generate sort-order const sortOrder = [] propertyGroups.forEach(group => { if (!group?.properties?.length) return sortOrder.push(...group.properties) }) // write sort-order.json let preset = { 'sort-order': sortOrder } const content = JSON.stringify(preset, null, 2) fs.writeFileSync(CSSCOMB_SORT_ORDER_FILE_PATH, content, 'utf8') // read preset-base.json const presetBaseContent = fs.readFileSync(CSSCOMB_PRESET_BASE_FILE_PATH, 'utf8') const presetBase = JSON.parse(presetBaseContent) // write preset.json preset = { ...presetBase, ...preset, } const presetContent = JSON.stringify(preset, null, 2) fs.writeFileSync(CSSCOMB_PRESET_CUSTOM_FILE_PATH, presetContent, 'utf8') })()
其中 preset-base.json 就是上一章节 csscomb.preset 所贴出来的内容,除了 sort-order 选项之外,其他基本上是不变的。其中 sort-order.json 只是本地的一份存档,可要可不要。最后生成的 preset-custom.json 文件才是供 vscode-csscomb 使用的配置。
preset-base.json
sort-order.json
preset-custom.json
vscode-csscomb
这个脚本生成的过程,我是将它存放在 iCloud Drive 中的。比如,今天写下文章的时候我发现 stylelint-config-recess-order 可更新,只要更新下依赖,然后执行 NPM Script 就 OK 了。
以上方式,势必在本地产生一个 node_modules 目录,但我们不希望里面成千上万的文件在 iCloud Drive 中同步。
node_modules
如果希望 iCloud Drive 上某个目录不同步,需在目录名称后加上 .nosync。
.nosync
但是,如果将 node_modules 修改为 node_modules.nosync,那么在执行脚本的时候,就会因为找不到 node_modules 而出错。这里可参考 nosync-icloud 的解决方案。
node_modules.nosync
原理大致是:创建一个名为 node_modules 的软链接至 node_modules.nosync 目录,而软链接文件内容只是存放一个文件地址,文件大小可忽略,所以它同步到 iCloud Drive 也问题不大。当脚本执行,在查找 node_modules 模块时,会指向真实的目录,所以也没问题。
背景
在使用 VS Code 编写代码时,通常会开启
editor.formatOnSave
选项以在保存时格式化文件。一般来说,对于大多数语言来说,VS Code 都有对应的内置格式化程序(formatter)。它们通常只会处理缩进、折行、前导尾随空格等操作。
如果内置的不够用,可以通过安装第三方插件以实现更多的可能。比如,将颜色值转为小写、改进 JavaScript 写法等都可以在保存文件时自动处理,具体取决于插件实现。
由于语言众多,格式化插件也很多,还可以支持配置默认的格式化程序。这个可以在文件编辑区右键选择「使用 ... 格式化」进行配置。比如:
现在很多工程化项目都会配置格式化处理,也可在 Git 的
pre-commit
勾子中跑一遍处理脚本,以确保提交到仓库的代码格式是统一的,尽管大家使用的编辑器可能有差异。虽说如此,仍然有必要我们的编辑器配置一些格式化程序,以便于在编写一些 Snippet、Demo 等的时候,也有着较为规范、格式统一的代码。尤其是像我这种强迫症患者。
个人用得最多的是 Prettier,主流编辑器都有对应插件,支持 JavaScript、HTML、CSS 以及对应变体等 Web 前端相关的语言。
诉求
目前我想要的是:在保存文件时,按一定的规则自动对 CSS 属性进行排序。此时 Prettier 就无能为力了。
对于 CSS 属性声明顺序,最初是因为看了 Code Guide by @AlloyTeam 的规范,目前里面提及的属性顺序已过时,最后维护时间已经是 2015 年了。有一句话我很喜欢(源自):
排序的好处无非就是快速看得出元素盒子所占的空间,是否有重复声明的属性等。
目前,本人所参考的是 Code Guide @mdo 规范,对应的 Stylelint 插件是 Bootstrap 在用的
stylelint-config-recess-order
,维护较为积极,也能紧跟最新的 CSS 属性,它们会按照以下分组排序(详见):与 Declaration order 相关的插件还有以下几个,有些已经好几年没更新了,仅供参考。
stylelint-config-rational-order
的 Prettier 插件)以上这些集成到项目里面是非常好用的,但对于单个文件或者工程化程度不高的项目,它们没办法施展才华。原因是它们都是基于 Stylelint 的插件
stylelint-order
实现的,而对应 VS Code 插件并不支持配置插件。因此,本文会借助一个名为 CSScomb.js 的格式化程序,它的主要功能便是「属性排序」,对应的 VS Code 插件是 vscode-csscomb。
尽管如此,它目前仍然足够好用。
配置
其中 vscode-csscomb 插件配置项有以下几个:
此处不展开说明,具体可看文档:
我的 VS Code 配置如下:
其中,对于像小程序等 WXSS 样式文件,可以在
csscomb.syntaxAssociations
进行关联,使其当成 CSS 一样去处理。由于
csscomb.preset
配置项非常地长(sort-order
造成的),也便于多设备同步,我选择将其存放到 iCloud Drive 目录。如下:以上都是一些比较常规的配置,其中一些也是为了跟 Prettier 保持一致而设置的。另外,为了避免影响篇幅以上
sort-order
配置省略了,可参考这里。生成 sort-order
由于 CSS 在不断的发展,为了让
sort-order
跟上最新标准,这里使用stylelint-config-recess-order
来生成。脚本很简单,仅供参考:
其中
preset-base.json
就是上一章节csscomb.preset
所贴出来的内容,除了sort-order
选项之外,其他基本上是不变的。其中sort-order.json
只是本地的一份存档,可要可不要。最后生成的preset-custom.json
文件才是供vscode-csscomb
使用的配置。这个脚本生成的过程,我是将它存放在 iCloud Drive 中的。比如,今天写下文章的时候我发现
stylelint-config-recess-order
可更新,只要更新下依赖,然后执行 NPM Script 就 OK 了。关于 node_modules 同步问题
以上方式,势必在本地产生一个
node_modules
目录,但我们不希望里面成千上万的文件在 iCloud Drive 中同步。但是,如果将
node_modules
修改为node_modules.nosync
,那么在执行脚本的时候,就会因为找不到node_modules
而出错。这里可参考 nosync-icloud 的解决方案。原理大致是:创建一个名为
node_modules
的软链接至node_modules.nosync
目录,而软链接文件内容只是存放一个文件地址,文件大小可忽略,所以它同步到 iCloud Drive 也问题不大。当脚本执行,在查找node_modules
模块时,会指向真实的目录,所以也没问题。References