Skip to content

Latest commit

 

History

History
454 lines (359 loc) · 9.27 KB

README_zh-CN.md

File metadata and controls

454 lines (359 loc) · 9.27 KB

vite-plugin-css-export 🥰

中文 | English

从 CSS 导出变量到 JS 中,并且支持嵌套规则。

npm package node compatibility vite compatibility

这个插件允许你在 CSS 中使用 :export 伪类,并且这个伪类下的属性将会被导出到 JavaScript 中。

除此之外,如果在 Vite 中启用了 CSS 预处理器,那我们就可以在 .scss、.sass、.less、.styl 和 .stylus 文件中使用 :export

如何在 Vite 中使用 CSS 预处理器

注意:Vite5 请使用 3.x,Vite4 请使用 2.x,Vite2 和 Vite3 请使用 1.x。

安装 ❤️

npm install vite-plugin-css-export -D

or

yarn add vite-plugin-css-export -D

or

pnpm add vite-plugin-css-export -D

使用 💡

快速上手

// vite.config.ts
import ViteCSSExportPlugin from 'vite-plugin-css-export'
import { defineConfig } from 'vite'

export default defineConfig({
  plugins: [ViteCSSExportPlugin()]
})
/* example.css */
:root {
  --font-color: #333;
}

:export {
  fontColor: var(--font-color);
  fontSize: 14px;
}

:export button {
  bgColor: #462dd3;
  color: #fff;
}

:export menu menuItem {
  bgColor: #1d243a;
  color: #fff;
}
// 如果使用了 Typescript ,你需要引用这个声明文件
// 里面包含了所需的通配符模块声明,如 *.css?export
// env.d.ts
/// <reference types="vite-plugin-css-export/client" />

// 如果你想要代码提示
interface CSSPropertiesExportedData {
  fontColor: string
  fontSize: string
  button: {
    bgColor: string
    color: string
  }
  menu: {
    menuItem: {
      bgColor: string
      color: string
    }
  }
}

在导入时,路径中需加入后缀 ?export

// main.ts
import cssResult from './assets/style/example.css?export'

console.log(cssResult)

// output
// {
//     fontColor: "var(--font-color)",
//     fontSize: "14px",
//     button: {
//         bgColor: "#462dd3",
//         color: "#fff"
//     },
//     menu: {
//         menuItem: {
//             bgColor: "#1d243a",
//             color: "#fff"
//         }
//     }
// }

CSS 预处理器

如果你启用了 CSS 预处理器,那么你可以使用嵌套规则,便于我们定义一些复杂的结构。

// .scss
:root {
  --font-color: #333;
}

$menuItemBgColor: #1d243a;

:export {
  fontColor: var(--font-color);
  fontSize: 14px;
  button {
    bgcolor: #462dd3;
    color: #fff;
  }
  menu {
    menuItem {
      bgcolor: $menuItemBgColor;
      color: #fff;
    }
  }
}

CSS Module

与 CSS module 一起使用时,需要进行一些简单的配置,默认情况下,导出的结果中不会包含 CSS module 的相关内容(除了:export下的内容)。

// vite.config.ts
import ViteCSSExportPlugin from 'vite-plugin-css-export'
import { defineConfig } from 'vite'

export default defineConfig({
  plugins: [
    ViteCSSExportPlugin({
      cssModule: {
        isGlobalCSSModule: false,
        enableExportMerge: true, // default false
        sharedDataExportName: 'cssExportedData' // default 'sharedData'
      }
    })
  ]
})
// example.module.scss
:root {
  --font-color: #333;
}

$menuItemBgColor: #1d243a;

.base-button {
  background-color: transparent;
}

// :export 的别名
:share {
  fontcolor: var(--font-color);
  fontsize: 14px;

  button {
    bgcolor: #462dd3;
    color: #fff;
  }

  menu {
    menuItem {
      bgcolor: $menuItemBgColor;
      color: #fff;
    }
  }
}

:export {
  fontColor: var(--font-color);
  fontSize: 14px;
}
// main.ts
import cssModuleResult from './assets/style/example.module.scss?export'

console.log(cssModuleResult)

// output
// {
//     cssExportedData: {
//         fontColor: "var(--font-color)",
//         fontSize: "14px",
//         button: {
//             bgColor: "#462dd3",
//             color: "#fff"
//         },
//         menu: {
//             menuItem: {
//                 bgColor: "#1d243a",
//                 color: "#fff"
//             }
//         }
//     },
//     fontColor: "var(--font-color)",
//     fontSize: "14px",
//     "base-button": "_base-button_1k9w3_5" // css module
// }

// 当 enableExportMerge 为 false时,将不会包含CSS module的相关内容
// output
// {
//     fontColor: "var(--font-color)",
//     fontSize: "14px",
//     button: {
//         bgColor: "#462dd3",
//         color: "#fff"
//     },
//     menu: {
//         menuItem: {
//             bgColor: "#1d243a",
//             color: "#fff"
//         }
//     }
// }

注意 ⚠

如果插件与 CSS module 一起使用,请将 :export 替换为 :share ,这样做可以避免与 CSS module 提供的:export之间的未知冲突。

实际上你仍然可以使用:export,它并不会导致运行错误,:share:export 的别名。

请不要在属性名称中键入以下字符:

"/", "~", ">", "<", "[", "]", "(", ")", ".", "#", "@", ":", "*"

由于本插件应用在vite:css之后,所以一切解析行为都基于vite:css返回的结果,当你键入以上字符时,存在一些字符本插件无法给出正确的警告/错误信息,例如:@

// your code
:export {
  fontColor: var(--font-color);
  fontSize: 14px;

  button {
    bgcolor: #462dd3;
    color: #fff;
  }

  @menu {
    menuItem {
      bgcolor: $menuItemBgColor;
      color: #fff;
    }
  }
}
/** after vite:css */
:export {
  fontColor: var(--font-color);
  fontSize: 14px;
}
:export button {
  bgColor: #462dd3;
  color: #fff;
}
/** 无法捕捉 @menu */
@menu {
  :export menuItem {
    bgColor: #1d243a;
    color: #fff;
  }
}
// after vite:css-export
{
  fontColor: "var(--font-color)",
  fontSize: "14px",
  button: {
    bgColor: "#462dd3",
    color: "#fff"
  },
  // menu 丢失
  menuItem: {
    bgColor: "#1d243a",
    color: "#fff"
  }
}

代码检查

你可能会得到编辑器或者 Stylelint 的一些警告,你可以把相关规则关闭。

VS Code

{
  "css.lint.unknownProperties": "ignore",
  "scss.lint.unknownProperties": "ignore",
  "less.lint.unknownProperties": "ignore"
}

Stylelint

{
  "rules": {
    "property-no-unknown": [
      true,
      {
        "ignoreSelectors": [":export", ":share"]
      }
    ],
    "property-case": null,
    "selector-pseudo-class-no-unknown": [
      true,
      {
        "ignorePseudoClasses": ["export", "share"]
      }
    ],
    "selector-type-no-unknown": [
      true,
      {
        "ignore": ["default-namespace"]
      }
    ]
  }
}

配置项 ⚙️

shouldTransform

  • type: (id: string) => boolean

  • default: undefined

  • description: 该选项允许你额外指定哪些样式文件应该被转换,而不仅仅是?export,用法如下:

// vite.config.ts
export default defineConfig({
  plugins: [
    ViteCSSExportPlugin({
      shouldTransform(id) {
        const include = path.resolve(
          process.cwd(),
          'example/assets/style/share-to-js'
        )
        return path.resolve(id).indexOf(include) > -1
      }
    })
  ]
})

propertyNameTransformer

  • type: (key: string) => string

  • default: undefined

  • description: 该选项允许你定义一个转换 CSS 属性名称的方法,它并不会处理 additionalData。插件内置了一些方法,用法如下:

// vite.config.ts
import {
  default as ViteCSSExportPlugin,
  kebabCaseToUpperCamelCase,
  kebabCaseToLowerCamelCase,
  kebabCaseToPascalCase
} from 'vite-plugin-css-export'

export default defineConfig({
  plugins: [
    ViteCSSExportPlugin({
      propertyNameTransformer: kebabCaseToUpperCamelCase
    })
  ]
})

additionalData

  • type: SharedCSSData

  • default: {}

  • description: 该选项允许你将指定的数据附加到所有的已处理的结果中,我们可以在这里分享一些常用的属性值。

cssModule

cssModule.isGlobalCSSModule

  • type: boolean

  • default: false

  • description: 是否在全局启用了 CSS module,而不仅仅是在 .module.[suffix] 文件中。

cssModule.enableExportMerge

  • type: boolean

  • default: false

  • description: 当值为 true 时, sharedData 将会和 CSS module 的内容合并后再导出, 否则只有 sharedData 会被导出。它在使用?inline时不会生效。

sharedData 是本插件处理 CSS 内容后的结果

cssModule.sharedDataExportName

  • type: string

  • default: 'sharedData'

  • description:cssModule.enableExportMerge 值为 true 时, 修改导出结果中 sharedData 的属性名称。它在使用?inline时不会生效。