CSS Modules
为每个局部类赋予全局惟一的类名,这样组件样式间就不会相互影响了。如:javascript
/* button.css */
.button {
font-size: 16px;
}
.mini {
font-size: 12px;
}
复制代码
它会被转换为相似这样:css
/* button.css */
.button__button--d8fj3 {
font-size: 16px;
}
.button__mini--f90jc {
font-size: 12px;
}
复制代码
当导入一个 CSS 模块文件时,它会将局部类名到全局类名的映射对象提供给咱们。就像这样:html
import styles from './button.css'
// styles = {
// button: 'button__button--d8fj3',
// mini: 'button__mini--f90jc'
// }
element.innerHTML = '<button class="' + styles.button + ' ' + styles.mini + '" />'
复制代码
vue-css-modules
:简化类名映射下面是一个使用了 CSS Modules 的按钮组件:vue
<template>
<button :class="{ 'global-button-class-name': true, [styles.button]: true, [styles.mini]: mini }">点我</button>
</template>
<script> import styles from './button.css' export default { props: { mini: Boolean }, data: () => ({ styles }) } </script>
复制代码
的确,CSS Modules 对于 Vue 组件是一个不错的选择。但也存在如下几点不足:java
data
中传入 styles
styles.localClassName
导入全局类名对于上面的按钮组件,使用 vue-css-modules
后:git
<template>
<button class="global-button-class-name" styleName="button :mini">
点我
</button>
</template>
<script> import CSSModules from 'vue-css-modules' import styles from './button.css' export default { mixins: [CSSModules(styles)], props: { mini: Boolean } } </script>
复制代码
如今:github
data
中传入 styles
,但得在 mixins
中传入 styles
🌝styles.localClassName
说拜拜了styleName
属性,全局类名放在 class
属性,规整了许多:
修饰符<button styleName="@button">按钮</button>
复制代码
这等同于:api
<button styleName="button" data-component-button="true">按钮</button>
复制代码
这让你能在外部重置组件的样式:模块化
.form [data-component-button] {
font-size: 20px;
}
复制代码
<button styleName="$type">按钮</button>
复制代码
这等同于:函数
<button :styleName="type">按钮</button>
复制代码
<button styleName=":mini">按钮</button>
复制代码
这等同于:
<button :styleName="mini ? 'mini' : ''">按钮</button>
复制代码
<button styleName="disabled=isDisabled">按钮</button>
复制代码
这等同于:
<button :styleName="isDisabled ? 'disabled' : ''">按钮</button>
复制代码
<template>
<button class="global-button-class-name" styleName="button :mini">
点我
</button>
</template>
<script> import CSSModules from 'vue-css-modules' import styles from './button.css' export default { mixins: [CSSModules(styles)], props: { mini: Boolean } } </script>
复制代码
<template>
<button class="global-button-class-name" styleName="button :mini">
点我
</button>
</template>
<script> import CSSModules from 'vue-css-modules' export default { mixins: [CSSModules()], props: { mini: Boolean } } </script>
<style module> .button { font-size: 16px; } .mini { font-size: 12px; } </style>
复制代码
import CSSModules from 'vue-css-modules'
import styles from './button.css'
export default {
mixins: [CSSModules(styles)],
props: { mini: Boolean },
render() {
return (
<button styleName="@button :mini">点我</button>
)
}
}
复制代码
import CSSModules from 'vue-css-modules'
import styles from './button.css'
export default {
mixins: [CSSModules(styles)],
props: { mini: Boolean },
render(h) {
return h('button', {
styleName: '@button :mini'
}, '点我')
}
}
复制代码
vue-css-modules
注册了 beforeCreate
钩子,在钩子中劫持了组件的渲染函数。对于传给渲染函数的参数,将会解析其 data
或 data.attrs
中的 styleName
属性生成全局类名字符串,并将它附着在 data.staticClass
值的后面。
Github:vue-css-modules