概述
一、什么是css-in-js
参考:【css in js 简介】
简单来说,传统的前端方案推崇"关注点分离"原则,HTML、CSS、JavaScript 应该各司其职,进行分离。
而在react项目中,更提倡组件化方案,自然形成了将HTML、CSS、JavaScript集中编写管理的方式。
开发方式由"关注点分离"变为了"关注点混合",成为了我们在react中所熟悉的写法:
const Widget = () => {
<div style={{
color: 'white',
fontSize: '12px'
}} onClick={() => doSometing()}>
text
</div>
}
但是这种写法的弊端在于,react中的style仅仅是简单的Object,不支持复杂的嵌套、选择器等特性,使用起来很不方便。 因此,便出现了大量的三方库来进行拓展,这些库统称为css-in-js。它们一般都支持样式嵌套、选择器、主题配置等特性。
有人专门统计了现有的css-in-js三方库,轮子不要太多: css in js 三方库一览 。比较流行的主要有: styled-components, emotion, glamorous。
尽管css-in-js带来许多好处,但仍有不足,在某些场景下使用仍然较繁琐。比如繁琐的将css属性映射到props中的操作、使用theme时需要写很长的解析表达式(props => props.theme.colors.primary
)等等。
因此,除了这些css-in-js库之外,还有人基于它们做了更进一步的封装,提供了一些标准api来方便我们更快速的使用css-in-js特性,比如:rebass,theme-ui。
二、css-in-js 的使用
基于emotion举例
emotion的用法示例
emotion 官方文档
emotion 同时支持 css props写法和styled写法
1.string + css props 写法
import { css, jsx } from '@emotion/core'
const color = 'white'
render(
<div
css={css`
padding: 32px;
background-color: hotpink;
font-size: 24px;
border-radius: 4px;
&:hover {
background-color: ${color};
}
`}
>
Hover to change color.
</div>
)
2.object + css props写法
import { css, jsx } from '@emotion/core'
const color = 'white'
render(
<div
css={{
padding: '32px',
backgroundColor: 'hotpink',
fontSize: '24px',
borderRadius: '4px',
'&:hover': {
backgroundColor: color
}
}}
>
Hover to change color.
</div>
)
3.string + styled 写法
import styled from '@emotion/styled'
const color = 'white'
const Button = styled.div`
padding: 32px;
background-color: hotpink;
font-size: 24px;
border-radius: 4px;
&:hover {
background-color: ${color};
}
`
render(<Button>This my button component.</Button>)
4.object + styled 写法
import styled from '@emotion/styled'
const color = 'white'
const Button = styled.div(
{
padding: '32px',
backgroundColor: 'hotpink',
fontSize: '24px',
borderRadius: '4px',
'&:hover': {
backgroundColor: color
}
}
)
render(<Button>This my button component.</Button>)
可以看到,
- string写法是纯粹的css样式,而object写法类似于react的style object,但是支持嵌套和selector。
- css props写法可以直接将样式写在组建中,而styled写法是先将组件封装成一个新的组件后再使用。
更多特性,请查看官方文档,此文不再赘述。
emotion 与 styled-components 如何选择
除了emotion之外,styled-components也比较常用
styled-components 官方文档
在使用上,styled-components 与 emotion 的styled写法一样,需要将组件封装成一个新的组件后再使用。
鉴于emotion已经支持了styled模式,可以优先选择emotion。
也可以参考theme-ui项目选择emotion的原因:
While there are many different solutions to handling CSS in JavaScript, Styled Components and Emotion have become the most widely-used industry-standard libraries. If you're building a custom component library, either Styled Components or Emotion should suit your needs just fine.
For Theme UI, the decision was primarily based on these factors:
- Emotion's implementation of the css prop and the custom JSX pragma allows for better integration with @styled-system/css
- The Emotion API includes more lower-level utilities, like createEmotion that could be leveraged when considering how multiple themes could be composed together
- Emotion's theming context is directly available in @emotion/core, allowing this library to leverage React's context API in different ways
- In the case of Theme UI internals, the styled higher-order component utility is not necessarily the best API for creating components, and by not including @emotion/styled in the core package the bundle size is kept to a minimum – i.e. most of the same things can be achieved with the css prop
Emotion 的css props 写法、以及其提供的一些比较底层的api更利于自定义组件。并且在不适用styled风格的情况下,包体积更小。
三、Rebass:更进一步&开箱即用
rebass带来了什么
Rebass是基于styled-system、emotion、styled-components构建的一个可定制组件库。基于Rebass可以快速的构建符合项目风格的基础组件。
不同于antd这类UI库,Rebass只提供几个原始的组件(Box、Flex、Text、Heading、Button、Link、Image、Card),这些组件都非常的初级,就像div一样。基于这些组件,以及Rebass的主题特性,我们很容易就可以定制出项目用到的组件。
Rebass支持多种方式来编写组件样式: - sx props:基于reflexbox实现,类似于emotion中的object css prop,并且能够直接使用theme中定义的主题属性 - style prop:基于styled-system实现 - css prop:继承emotion的用法 - styled:继承emotion的用法
几种用法举例:
// theme.js
export default {
colors: {
primary: 'red'
},
variants: {
badge: {
display: 'inline-block',
p: 1,
color: 'white',
bg: 'primary',
borderRadius: 2,
}
},
}
// 1.sx prop
<Box variants="badge" sx={{
bg: 'primary',
height: '100px'
}}>
<Text>123</Text>
</Box>
// 2.style prop
<Box variants="badge" bg='primary' height='100px'>
<Text>123</Text>
</Box>
从例子中可以看到: - 在rebass组件中我们可以直接通过theme的key来使用主题样式,而不用写诸如props => props.theme.colors.primary
之类的繁琐语句。 - 我们可以把css属性当做普通的prop传入组件(height),而不用做任何额外的操作。 - 我们可以通过variants来包裹一组css样式,使得主题具备了类似class的功能。这个是非常有用的一个功能,简化了主题样式的使用,并提高了可复用性。
rebass是如何做到的
Rebass库的源码非常少,主要是整合了reflexbox、styled-system以及styled-components的特性。
reflexbox
reflexbox文档
reflexbox基于Emotion和Styled Components实现,提供了两个具有响应式特性的组件:Box和Flex。除此以外,提供了sx prop特性来编写样式,遵循主题样式规范,完美支持主题定制。
可以说Rebass的主要特性全部由reflexbox实现,仅仅是在其之上做了一层封装,定制了几个基础组件,并提供了对styled-components的支持。
styled-system
styled-system 官方文档
Styled System is a collection of utility functions that add style props to your React components and allows you to control styles based on a global theme object with typographic scales, colors, and layout properties.
Styled System 提供了一系列工具方法来给React组件添加样式属性,并且支持使用全局样式来控制组件的尺寸、颜色和布局等属性。
不好理解?可以看一个简答的例子,我们有一个白色组件,常规写法如下:
.white-block {
color: '#fff'
}
<Compnent className="white-block"/>
通过styled-system包装后,可以把color作为一个props放入组件中。类似于给html element增加自定义标签。
// 定义组件
import styled from '@emotion/styled'
import { color } from 'styled-system'
const Compnent = styled.div`
${color}
`
export default Compnent
// 使用组件,这里包装后不仅提供了color属性,也提供了bg(background-color)属性
<Compnent color='#fff' bg='red'/>
这就是文档中提到的:
Styled System is a collection of utility functions that add style props to your React components
styled-system 是如何工作的
官方说明链接
继续上面的例子,${color}
里面有什么魔法? 实际上,从styled-system导入的color是一个类似于这样的函数
props => `color: ${props.color}; background-color: ${props.bg}`
正如描述中所说,styled-system就是帮我们把css归类,并包装成了一些可以在emotion或者styled-components这类css-in-js库中使用的工具方法,方便我们使用。
四、结语
除了文章中介绍的内容外,css-in-js还支持许多好用的特性,比如响应式布局、选择器、动画等等。
如果想体验css-in-js,可以先试试Emotion,了解一些基本的原理,然后直接上Rebass吧,用起来还是挺香的。
欢迎留言交流~
关于我们
深圳市浅海科技有限公司
我们是一个高效、热情、有责任的技术团队,承接各种软件系统定制需求。
长期招聘远程开发者,如果您喜欢尝试新技术,有一点代码洁癖,能够使用文档进行高效的沟通,React/nodejs/ES6任意一种玩的飞起,那么,欢迎来撩~(想赚快钱的请绕道,谢谢)
简历请发送到:service@qianhaikeji.cn
当然,也欢迎甲方爸爸把项目甩我们脸上。
最后
以上就是冷静寒风为你收集整理的js button onclick 传参_谈一谈css-in-js在React项目中的使用的全部内容,希望文章能够帮你解决js button onclick 传参_谈一谈css-in-js在React项目中的使用所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复