React中样式隔离

558 阅读2分钟

使用id做为隔离域

每个views顶层有且只有一个idid命名为views目录名),它下面的所有样式都在此id的作用域下。它的好处是样式方便透传,并且样式会单独抽成css文件,方便一些样式的抽取合并。

使用styled-jsx

使用styled-jsx,类似vue,直接在样式名上产生hash值,达到隔离的目的。它的好处是样式完全在组件内,方便组件复用,但它的样式会打包在相应的js中
组件内模块化样式
export default () => {
    return (
        <div className="c-skeleton">
            <div className="c-title">Name</div>
            <style jsx>{`
                .c-skeleton {
                    color: 'red'
                }
                .c-title {
                    color: 'blue'
                }
            `}
            </style>
        </div>
    )
}
将模块化样式单独提取到一个文件的写法:
// index._less
.c-skeleton {
    color: red;
}

// index.js
import React from 'react';
import styled from './index._less';
export default () => {
    return (
        
        <>
            <div className="c-skeleton">Name</div>
            <style jsx>{styled}</style>
        </>
    )
}
styled-jsx会在打包过程中,将:
<style>
.c-footer {
    width: 1200px;
    margin: 0 auto;
    border-top: 1px solid #ccc;
}

</style>
转化为
<style>

.c-footer.jsx-69286511 {
    width: 1200px;
    margin: 0 auto;
    border-top: 1px solid #ccc;
}

</style>

使用css模块化后,模块化后组件的样式将不会影响当前样式名,且不会渗透到子组件中。不过,模块化组件的样式会被父组件的作用域样式影响。这样设计是为了让父组件可以从布局的角度出发,调整其子组件元素的样式。

使用模块化的css,公共部分不会被mini-css-extract-plugin抽取,但它们会随着组件的卸载而自动被卸载。

使用js文件写css
它的好处是可以动态做计算,目前_less文件不能直接引入相对路径的图片,但通过js文件的方式,可通过import形式引入图片。
import css from 'styled-jsx/css'
import logo from './skeleton.svg?src'
import logoSvg from './images/logosvg.svg?type=src' // ?type=src 代表以路径的方式引用svg,而不是转换成react组件
export default css`

.c-skeleton {
    padding: 70px 0 60px;
    text-align: center;
}

.c-logo {
    background: url(${logo})
}

.c-logo-svg {
    backgournd: url(${logoSvg})
}

.c-title {
    padding-top: 20px;
    font-size: 20px;
    line-height: 30px;
    color: #333;
}
`